diff options
Diffstat (limited to 'lbaselib.c')
| -rw-r--r-- | lbaselib.c | 40 |
1 files changed, 33 insertions, 7 deletions
| @@ -1,5 +1,5 @@ | |||
| 1 | /* | 1 | /* |
| 2 | ** $Id: lbaselib.c,v 1.156 2004/08/30 18:35:14 roberto Exp roberto $ | 2 | ** $Id: lbaselib.c,v 1.157 2004/09/03 13:16:48 roberto Exp roberto $ |
| 3 | ** Basic library | 3 | ** Basic library |
| 4 | ** See Copyright Notice in lua.h | 4 | ** See Copyright Notice in lua.h |
| 5 | */ | 5 | */ |
| @@ -523,9 +523,13 @@ static int auxresume (lua_State *L, lua_State *co, int narg) { | |||
| 523 | int status; | 523 | int status; |
| 524 | if (!lua_checkstack(co, narg)) | 524 | if (!lua_checkstack(co, narg)) |
| 525 | luaL_error(L, "too many arguments to resume"); | 525 | luaL_error(L, "too many arguments to resume"); |
| 526 | if (lua_threadstatus(co) == 0 && lua_gettop(co) == 0) { | ||
| 527 | lua_pushliteral(L, "cannot resume dead coroutine"); | ||
| 528 | return -1; /* error flag */ | ||
| 529 | } | ||
| 526 | lua_xmove(L, co, narg); | 530 | lua_xmove(L, co, narg); |
| 527 | status = lua_resume(co, narg); | 531 | status = lua_resume(co, narg); |
| 528 | if (status == 0) { | 532 | if (status == 0 || status == LUA_YIELD) { |
| 529 | int nres = lua_gettop(co); | 533 | int nres = lua_gettop(co); |
| 530 | if (!lua_checkstack(L, nres)) | 534 | if (!lua_checkstack(L, nres)) |
| 531 | luaL_error(L, "too many results to resume"); | 535 | luaL_error(L, "too many results to resume"); |
| @@ -599,22 +603,44 @@ static int luaB_costatus (lua_State *L) { | |||
| 599 | luaL_argcheck(L, co, 1, "coroutine expected"); | 603 | luaL_argcheck(L, co, 1, "coroutine expected"); |
| 600 | if (L == co) lua_pushliteral(L, "running"); | 604 | if (L == co) lua_pushliteral(L, "running"); |
| 601 | else { | 605 | else { |
| 602 | lua_Debug ar; | 606 | switch (lua_threadstatus(co)) { |
| 603 | if (lua_getstack(co, 0, &ar) == 0 && lua_gettop(co) == 0) | 607 | case LUA_YIELD: |
| 604 | lua_pushliteral(L, "dead"); | 608 | lua_pushliteral(L, "suspended"); |
| 605 | else | 609 | break; |
| 606 | lua_pushliteral(L, "suspended"); | 610 | case 0: { |
| 611 | lua_Debug ar; | ||
| 612 | if (lua_getstack(co, 0, &ar) > 0) /* does it have frames? */ | ||
| 613 | lua_pushliteral(L, "normal"); /* it is running */ | ||
| 614 | else if (lua_gettop(co) == 0) | ||
| 615 | lua_pushliteral(L, "dead"); | ||
| 616 | else | ||
| 617 | lua_pushliteral(L, "suspended"); /* initial state */ | ||
| 618 | break; | ||
| 619 | } | ||
| 620 | default: /* some error occured */ | ||
| 621 | lua_pushliteral(L, "dead"); | ||
| 622 | break; | ||
| 623 | } | ||
| 607 | } | 624 | } |
| 608 | return 1; | 625 | return 1; |
| 609 | } | 626 | } |
| 610 | 627 | ||
| 611 | 628 | ||
| 629 | static int luaB_cocurrent (lua_State *L) { | ||
| 630 | if (lua_pushthread(L)) | ||
| 631 | return 0; /* main thread is not a coroutine */ | ||
| 632 | else | ||
| 633 | return 1; | ||
| 634 | } | ||
| 635 | |||
| 636 | |||
| 612 | static const luaL_reg co_funcs[] = { | 637 | static const luaL_reg co_funcs[] = { |
| 613 | {"create", luaB_cocreate}, | 638 | {"create", luaB_cocreate}, |
| 614 | {"wrap", luaB_cowrap}, | 639 | {"wrap", luaB_cowrap}, |
| 615 | {"resume", luaB_coresume}, | 640 | {"resume", luaB_coresume}, |
| 616 | {"yield", luaB_yield}, | 641 | {"yield", luaB_yield}, |
| 617 | {"status", luaB_costatus}, | 642 | {"status", luaB_costatus}, |
| 643 | {"current", luaB_cocurrent}, | ||
| 618 | {NULL, NULL} | 644 | {NULL, NULL} |
| 619 | }; | 645 | }; |
| 620 | 646 | ||
