rev 571 - trunk/src
SVN User <[email protected]> Fri, 04 Jun 2004 14:56:22 -0400
| Newsgroups | gmane.comp.lang.prothon.cvs |
|---|---|
| Message-ID | <[email protected]> |
Author: mark
Date: 2004-06-04 14:56:19 -0400 (Fri, 04 Jun 2004)
New Revision: 571
Modified:
trunk/src/interp.c
trunk/src/interp.h
Log:
fixed bugs in calling generators more than once
Modified: trunk/src/interp.c
===================================================================
--- trunk/src/interp.c 2004-06-04 17:01:42 UTC (rev 570)
+++ trunk/src/interp.c 2004-06-04 18:56:19 UTC (rev 571)
@@ -107,8 +107,9 @@
frame_p frame;
code_p code = NULL;
size_t flen;
- if (func_obj) code = obj_data_p(func_obj);
- else code = code_in;
+ if (code_in) code = code_in;
+ else if (func_obj) code = obj_data_p(func_obj);
+ pr_assert(code);
flen = sizeof(frame_t) + ( code ? (code->max_stack_depth+STACK_PADDING) * sizeof(obj_p) : 0 );
frame = pr_malloc(flen);
memset(frame, 0, flen);
@@ -1062,13 +1063,12 @@
}
#endif
if (op == OP_GEN) {
- obj_p new_locals = NEW_OBJ(NULL);
- frame_p new_frame = create_frame( ist, NULL, NULL, frame->locals,
- new_locals, func, NULL, NULL );
- new_frame->gen_marker = func;
+ gen_p genp = pr_malloc(sizeof(gen_t));
+ genp->frame = NULL;
+ genp->codep = func->data.ptr;
func->data.ptr = NULL;
switch_proto(ist, func, OBJ(GEN_PROTO));
- func->data.ptr = new_frame;
+ func->data.ptr = genp;
}
set_item(ist, fr_stack[fr_sp], fr_stack[fr_sp+1], func);
} break;
@@ -1224,12 +1224,17 @@
switch_frame = new_frame;
fr_push(OBJ(NONE));
} else if (has_proto(ist, func_obj, OBJ(GEN_PROTO))) {
- frame_p tmp_frame;
+ gen_p genp = func_obj->data.ptr;
+ code_p codep = genp->codep;
+ obj_p new_locals;
+
IF_EXC_BREAK;
- pr_assert(func_obj->data.ptr);
- tmp_frame = func_obj->data.ptr;
- frame->next_frame = tmp_frame;
- load_frame_params(ist, tmp_frame->locals, func_obj, param*2, fr_stack+fr_sp+2);
+ new_locals = NEW_OBJ(NULL);
+ genp->frame = create_frame( ist, NULL, NULL, frame->locals,
+ new_locals, func_obj, codep, NULL );
+ genp->frame->gen_marker = func_obj;
+ frame->next_frame = genp->frame;
+ load_frame_params(ist, genp->frame->locals, func_obj, param*2, fr_stack+fr_sp+2);
IF_EXC_BREAK;
fr_push(func_obj);
} else {
@@ -1334,7 +1339,8 @@
break;
}
if (fr_stack[fr_sp+1] == SYM(NEXT) && has_proto(ist, fr_stack[fr_sp], OBJ(GEN_PROTO))) {
- frame_p new_frame=(frame_p)(fr_stack[fr_sp]->data.ptr);
+ gen_p genp = fr_stack[fr_sp]->data.ptr;
+ frame_p new_frame = genp->frame;
if (!new_frame) {
raise_exception(ist, OBJ(STOP_ITERATION_EXC), NULL);
break;
@@ -1410,12 +1416,16 @@
switch_frame = new_frame;
fr_push(OBJ(NONE));
} else if (has_proto(ist, func_obj, OBJ(GEN_PROTO))) {
- frame_p tmp_frame;
+ gen_p genp = func_obj->data.ptr;
+ code_p codep = genp->codep;
+ obj_p new_locals;
IF_EXC_BREAK;
- pr_assert(func_obj->data.ptr);
- tmp_frame = func_obj->data.ptr;
- frame->next_frame = tmp_frame;
- load_frame_params(ist, tmp_frame->locals, func_obj, param*2, fr_stack+fr_sp+3);
+ new_locals = NEW_OBJ(NULL);
+ genp->frame = create_frame( ist, NULL, NULL, frame->locals,
+ new_locals, func_obj, codep, NULL );
+ genp->frame->gen_marker = func_obj;
+ frame->next_frame = genp->frame;
+ load_frame_params(ist, genp->frame->locals, func_obj, param*2, fr_stack+fr_sp+3);
IF_EXC_BREAK;
fr_push(func_obj);
} else {
@@ -1562,8 +1572,10 @@
#endif
stack_lim = frame->code->max_stack_depth;
// free_frame(tmp_frame); XXX
- if (tmp_frame->gen_marker)
- tmp_frame->gen_marker->data.ptr = NULL;
+ if (tmp_frame->gen_marker) {
+ gen_p genp = tmp_frame->gen_marker->data.ptr;
+ genp->frame = NULL;
+ }
if (!tmp_frame->do_not_free)
pr_free(tmp_frame);
frame->next_frame = NULL;
Modified: trunk/src/interp.h
===================================================================
--- trunk/src/interp.h 2004-06-04 17:01:42 UTC (rev 570)
+++ trunk/src/interp.h 2004-06-04 18:56:19 UTC (rev 571)
@@ -113,6 +113,13 @@
obj_p free_label_list_obj;
} fparam_proc_state_t;
+typedef struct {
+ code_p codep;
+ frame_p frame;
+} gen_t;
+
+typedef gen_t* gen_p;
+
frame_p create_frame( isp ist, obj_p self, obj_p syn_locals, obj_p dyn_locals,
obj_p locals, obj_p func_obj, code_p code_in, char* name );