ViewVC Help
View File | Revision Log | Show Annotations | Download File
/cvs/Coro/Coro/State.xs
(Generate patch)

Comparing Coro/Coro/State.xs (file contents):
Revision 1.147 by root, Mon Mar 19 15:50:48 2007 UTC vs.
Revision 1.148 by root, Fri Apr 13 12:56:55 2007 UTC

129}; 129};
130 130
131static size_t coro_stacksize = CORO_STACKSIZE; 131static size_t coro_stacksize = CORO_STACKSIZE;
132static struct CoroAPI coroapi; 132static struct CoroAPI coroapi;
133static AV *main_mainstack; /* used to differentiate between $main and others */ 133static AV *main_mainstack; /* used to differentiate between $main and others */
134static JMPENV *main_top_env;
134static HV *coro_state_stash, *coro_stash; 135static HV *coro_state_stash, *coro_stash;
135static SV *coro_mortal; /* will be freed after next transfer */ 136static SV *coro_mortal; /* will be freed after next transfer */
136 137
137static struct coro_cctx *cctx_first; 138static struct coro_cctx *cctx_first;
138static int cctx_count, cctx_idle; 139static int cctx_count, cctx_idle;
587 coro_mortal = 0; 588 coro_mortal = 0;
588 } 589 }
589} 590}
590 591
591/* inject a fake call to Coro::State::_cctx_init into the execution */ 592/* inject a fake call to Coro::State::_cctx_init into the execution */
593/* _cctx_init shoukld be careful, as it could be called at almost any time */
594/* during execution of a pelr program */
592static void NOINLINE 595static void NOINLINE
593prepare_cctx (pTHX_ coro_cctx *cctx) 596prepare_cctx (pTHX_ coro_cctx *cctx)
594{ 597{
595 dSP; 598 dSP;
596 LOGOP myop; 599 LOGOP myop;
607 PL_op = (OP *)&myop; 610 PL_op = (OP *)&myop;
608 PL_op = PL_ppaddr[OP_ENTERSUB](aTHX); 611 PL_op = PL_ppaddr[OP_ENTERSUB](aTHX);
609 SPAGAIN; 612 SPAGAIN;
610} 613}
611 614
615/*
616 * this is a _very_ stripped down perl interpreter ;)
617 */
612static void 618static void
613coro_run (void *arg) 619coro_run (void *arg)
614{ 620{
615 dTHX; 621 dTHX;
616 622
617 /* coro_run is the alternative tail of transfer(), so unlock here. */ 623 /* coro_run is the alternative tail of transfer(), so unlock here. */
618 UNLOCK; 624 UNLOCK;
619 625
620 /*
621 * this is a _very_ stripped down perl interpreter ;)
622 */
623 PL_top_env = &PL_start_env; 626 PL_top_env = &PL_start_env;
624 627
625 /* inject call to cctx_init */ 628 /* inject a fake subroutine call to cctx_init */
626 prepare_cctx (aTHX_ (coro_cctx *)arg); 629 prepare_cctx (aTHX_ (coro_cctx *)arg);
627 630
628 /* somebody will hit me for both perl_run and PL_restartop */ 631 /* somebody or something will hit me for both perl_run and PL_restartop */
629 PL_restartop = PL_op; 632 PL_restartop = PL_op;
630 perl_run (PL_curinterp); 633 perl_run (PL_curinterp);
631 634
632 fputs ("FATAL: C coroutine fell over the edge of the world, aborting. Did you call exit in a coroutine?\n", stderr); 635 /* If perl-run returns we assume exit() was being called, which */
633 abort (); 636 /* seems to be the only valid (non-bug) reason for perl_run to return. */
637 /* We try to exit by jumping to the bootstrap-time "top" top_env, as */
638 /* we cannot restore the "main" coroutine as Coro has no such concept */
639 PL_top_env = main_top_env;
640 JMPENV_JUMP (2); /* I do not feel well about the hardcoded 2 at all */
634} 641}
635 642
636static coro_cctx * 643static coro_cctx *
637cctx_new () 644cctx_new ()
638{ 645{
1175 newCONSTSUB (coro_state_stash, "SAVE_DEFFH", newSViv (CORO_SAVE_DEFFH)); 1182 newCONSTSUB (coro_state_stash, "SAVE_DEFFH", newSViv (CORO_SAVE_DEFFH));
1176 newCONSTSUB (coro_state_stash, "SAVE_DEF", newSViv (CORO_SAVE_DEF)); 1183 newCONSTSUB (coro_state_stash, "SAVE_DEF", newSViv (CORO_SAVE_DEF));
1177 newCONSTSUB (coro_state_stash, "SAVE_ALL", newSViv (CORO_SAVE_ALL)); 1184 newCONSTSUB (coro_state_stash, "SAVE_ALL", newSViv (CORO_SAVE_ALL));
1178 1185
1179 main_mainstack = PL_mainstack; 1186 main_mainstack = PL_mainstack;
1187 main_top_env = PL_top_env;
1188
1189 while (main_top_env->je_prev)
1190 main_top_env = main_top_env->je_prev;
1180 1191
1181 coroapi.ver = CORO_API_VERSION; 1192 coroapi.ver = CORO_API_VERSION;
1182 coroapi.transfer = api_transfer; 1193 coroapi.transfer = api_transfer;
1183 1194
1184 assert (("PRIO_NORMAL must be 0", !PRIO_NORMAL)); 1195 assert (("PRIO_NORMAL must be 0", !PRIO_NORMAL));

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines