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.169 by root, Thu Sep 27 16:25:10 2007 UTC vs.
Revision 1.170 by root, Thu Sep 27 20:14:49 2007 UTC

937 cctx_first = cctx; 937 cctx_first = cctx;
938} 938}
939 939
940/** coroutine switching *****************************************************/ 940/** coroutine switching *****************************************************/
941 941
942/* never call directly, always through the coro_state_transfer global variable */ 942static void NOINLINE
943transfer_check (pTHX_ struct coro *prev, struct coro *next)
944{
945 if (prev != next)
946 {
947 if (!(prev->flags & (CF_RUNNING | CF_NEW)))
948 croak ("Coro::State::transfer called with non-running/new prev Coro::State, but can only transfer from running or new states");
949
950 if (next->flags & CF_RUNNING)
951 croak ("Coro::State::transfer called with running next Coro::State, but can only transfer to inactive states");
952
953 if (next->flags & CF_DESTROYED)
954 croak ("Coro::State::transfer called with destroyed next Coro::State, but can only transfer to inactive states");
955
956 if (PL_lex_state != LEX_NOTPARSING)
957 croak ("Coro::State::transfer called while parsing, but this is not supported");
958 }
959}
960
961/* always use the TRANSFER macro */
943static void NOINLINE 962static void NOINLINE
944transfer (pTHX_ struct coro *prev, struct coro *next) 963transfer (pTHX_ struct coro *prev, struct coro *next)
945{ 964{
946 dSTACKLEVEL; 965 dSTACKLEVEL;
947 966
960 /* create a new empty context */ 979 /* create a new empty context */
961 Newz (0, prev->cctx, 1, coro_cctx); 980 Newz (0, prev->cctx, 1, coro_cctx);
962 prev->flags &= ~CF_NEW; 981 prev->flags &= ~CF_NEW;
963 prev->flags |= CF_RUNNING; 982 prev->flags |= CF_RUNNING;
964 } 983 }
965
966 /*TODO: must not croak here */
967 if (!prev->flags & CF_RUNNING)
968 croak ("Coro::State::transfer called with non-running prev Coro::State, but can only transfer from running states");
969
970 if (next->flags & CF_RUNNING)
971 croak ("Coro::State::transfer called with running next Coro::State, but can only transfer to inactive states");
972
973 if (next->flags & CF_DESTROYED)
974 croak ("Coro::State::transfer called with destroyed next Coro::State, but can only transfer to inactive states");
975 984
976 prev->flags &= ~CF_RUNNING; 985 prev->flags &= ~CF_RUNNING;
977 next->flags |= CF_RUNNING; 986 next->flags |= CF_RUNNING;
978 987
979 LOCK; 988 LOCK;
1026{ 1035{
1027 struct coro *prev, *next; 1036 struct coro *prev, *next;
1028}; 1037};
1029 1038
1030#define TRANSFER(ta) transfer (aTHX_ (ta).prev, (ta).next) 1039#define TRANSFER(ta) transfer (aTHX_ (ta).prev, (ta).next)
1040#define TRANSFER_CHECK(ta) transfer_check (aTHX_ (ta).prev, (ta).next)
1031 1041
1032/** high level stuff ********************************************************/ 1042/** high level stuff ********************************************************/
1033 1043
1034static int 1044static int
1035coro_state_destroy (pTHX_ struct coro *coro) 1045coro_state_destroy (pTHX_ struct coro *coro)
1123static void 1133static void
1124prepare_transfer (pTHX_ struct transfer_args *ta, SV *prev_sv, SV *next_sv) 1134prepare_transfer (pTHX_ struct transfer_args *ta, SV *prev_sv, SV *next_sv)
1125{ 1135{
1126 ta->prev = SvSTATE (prev_sv); 1136 ta->prev = SvSTATE (prev_sv);
1127 ta->next = SvSTATE (next_sv); 1137 ta->next = SvSTATE (next_sv);
1138 TRANSFER_CHECK (*ta);
1128} 1139}
1129 1140
1130static void 1141static void
1131api_transfer (SV *prev_sv, SV *next_sv) 1142api_transfer (SV *prev_sv, SV *next_sv)
1132{ 1143{
1249 break; 1260 break;
1250 } 1261 }
1251 1262
1252 /* free this only after the transfer */ 1263 /* free this only after the transfer */
1253 prev_sv = SvRV (coro_current); 1264 prev_sv = SvRV (coro_current);
1254 SvRV_set (coro_current, next_sv);
1255 ta->prev = SvSTATE (prev_sv); 1265 ta->prev = SvSTATE (prev_sv);
1256 1266 TRANSFER_CHECK (*ta);
1257 assert (ta->next->flags & CF_READY); 1267 assert (ta->next->flags & CF_READY);
1258 ta->next->flags &= ~CF_READY; 1268 ta->next->flags &= ~CF_READY;
1269 SvRV_set (coro_current, next_sv);
1259 1270
1260 LOCK; 1271 LOCK;
1261 free_coro_mortal (aTHX); 1272 free_coro_mortal (aTHX);
1262 coro_mortal = prev_sv; 1273 coro_mortal = prev_sv;
1263 UNLOCK; 1274 UNLOCK;

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines