diff options
author | Roberto Ierusalimschy <roberto@inf.puc-rio.br> | 2014-11-10 15:41:36 -0200 |
---|---|---|
committer | Roberto Ierusalimschy <roberto@inf.puc-rio.br> | 2014-11-10 15:41:36 -0200 |
commit | 79b0d05480668c36e15e26ff8b8ec0e9b3c54b2b (patch) | |
tree | 08af777a7c8924f50d30471bded74120f7fad240 | |
parent | 779381fe9e8fc3dea184d5d9de0d3170e9b64772 (diff) | |
download | lua-79b0d05480668c36e15e26ff8b8ec0e9b3c54b2b.tar.gz lua-79b0d05480668c36e15e26ff8b8ec0e9b3c54b2b.tar.bz2 lua-79b0d05480668c36e15e26ff8b8ec0e9b3c54b2b.zip |
new function 'T.checkpanic' (to check panic errors)
-rw-r--r-- | ltests.c | 53 |
1 files changed, 52 insertions, 1 deletions
@@ -1,5 +1,5 @@ | |||
1 | /* | 1 | /* |
2 | ** $Id: ltests.c,v 2.193 2014/11/07 18:07:17 roberto Exp roberto $ | 2 | ** $Id: ltests.c,v 2.194 2014/11/10 14:47:29 roberto Exp roberto $ |
3 | ** Internal Module for Debugging of the Lua Implementation | 3 | ** Internal Module for Debugging of the Lua Implementation |
4 | ** See Copyright Notice in lua.h | 4 | ** See Copyright Notice in lua.h |
5 | */ | 5 | */ |
@@ -11,6 +11,7 @@ | |||
11 | 11 | ||
12 | 12 | ||
13 | #include <limits.h> | 13 | #include <limits.h> |
14 | #include <setjmp.h> | ||
14 | #include <stdio.h> | 15 | #include <stdio.h> |
15 | #include <stdlib.h> | 16 | #include <stdlib.h> |
16 | #include <string.h> | 17 | #include <string.h> |
@@ -48,6 +49,9 @@ int islocked = 0; | |||
48 | #define obj_at(L,k) (L->ci->func + (k)) | 49 | #define obj_at(L,k) (L->ci->func + (k)) |
49 | 50 | ||
50 | 51 | ||
52 | static int runC (lua_State *L, lua_State *L1, const char *pc); | ||
53 | |||
54 | |||
51 | static void setnameval (lua_State *L, const char *name, int val) { | 55 | static void setnameval (lua_State *L, const char *name, int val) { |
52 | lua_pushstring(L, name); | 56 | lua_pushstring(L, name); |
53 | lua_pushinteger(L, val); | 57 | lua_pushinteger(L, val); |
@@ -902,6 +906,49 @@ static int int2fb_aux (lua_State *L) { | |||
902 | } | 906 | } |
903 | 907 | ||
904 | 908 | ||
909 | struct Aux { jmp_buf jb; const char *msg; }; | ||
910 | |||
911 | /* | ||
912 | ** does a long-jump back to "main program". | ||
913 | */ | ||
914 | static int panicback (lua_State *L) { | ||
915 | struct Aux *b; | ||
916 | const char *msg = lua_tostring(L, -1); | ||
917 | lua_pop(L, 1); | ||
918 | lua_getfield(L, LUA_REGISTRYINDEX, "_jmpbuf"); /* get 'Aux' struct */ | ||
919 | b = (struct Aux *)lua_touserdata(L, -1); | ||
920 | lua_pop(L, 1); /* remove 'Aux' struct */ | ||
921 | b->msg = msg; | ||
922 | longjmp(b->jb, 1); | ||
923 | return 1; /* to avoid warnings */ | ||
924 | } | ||
925 | |||
926 | static int checkpanic (lua_State *L) { | ||
927 | struct Aux b; | ||
928 | void *ud; | ||
929 | const char *code = luaL_checkstring(L, 1); /* create new state */ | ||
930 | lua_Alloc f = lua_getallocf(L, &ud); | ||
931 | lua_State *L1 = lua_newstate(f, ud); | ||
932 | if (L1 == NULL) { /* error? */ | ||
933 | lua_pushnil(L); | ||
934 | return 1; | ||
935 | } | ||
936 | lua_atpanic(L1, panicback); /* set its panic function */ | ||
937 | lua_pushlightuserdata(L1, &b); | ||
938 | lua_setfield(L1, LUA_REGISTRYINDEX, "_jmpbuf"); /* store 'Aux' struct */ | ||
939 | if (setjmp(b.jb) == 0) { /* set jump buffer */ | ||
940 | runC(L, L1, code); /* run code unprotected */ | ||
941 | lua_pushliteral(L, "no errors"); | ||
942 | } | ||
943 | else { /* error handling */ | ||
944 | /* move error message to original state */ | ||
945 | lua_pushstring(L, b.msg); | ||
946 | } | ||
947 | lua_close(L1); | ||
948 | return 1; | ||
949 | } | ||
950 | |||
951 | |||
905 | 952 | ||
906 | /* | 953 | /* |
907 | ** {====================================================== | 954 | ** {====================================================== |
@@ -1256,6 +1303,9 @@ static int runC (lua_State *L, lua_State *L1, const char *pc) { | |||
1256 | int i = getindex; | 1303 | int i = getindex; |
1257 | lua_pushboolean(L1, luaL_testudata(L1, i, getstring) != NULL); | 1304 | lua_pushboolean(L1, luaL_testudata(L1, i, getstring) != NULL); |
1258 | } | 1305 | } |
1306 | else if EQ("error") { | ||
1307 | lua_error(L1); | ||
1308 | } | ||
1259 | else if EQ("throw") { | 1309 | else if EQ("throw") { |
1260 | #if defined(__cplusplus) | 1310 | #if defined(__cplusplus) |
1261 | static struct X { int x; } x; | 1311 | static struct X { int x; } x; |
@@ -1453,6 +1503,7 @@ static const struct luaL_Reg tests_funcs[] = { | |||
1453 | {"listk", listk}, | 1503 | {"listk", listk}, |
1454 | {"listlocals", listlocals}, | 1504 | {"listlocals", listlocals}, |
1455 | {"loadlib", loadlib}, | 1505 | {"loadlib", loadlib}, |
1506 | {"checkpanic", checkpanic}, | ||
1456 | {"newstate", newstate}, | 1507 | {"newstate", newstate}, |
1457 | {"newuserdata", newuserdata}, | 1508 | {"newuserdata", newuserdata}, |
1458 | {"num2int", num2int}, | 1509 | {"num2int", num2int}, |