diff options
author | Roberto Ierusalimschy <roberto@inf.puc-rio.br> | 2010-04-19 13:36:06 -0300 |
---|---|---|
committer | Roberto Ierusalimschy <roberto@inf.puc-rio.br> | 2010-04-19 13:36:06 -0300 |
commit | 26d4a7396248623985b59d7e027cfecee561f446 (patch) | |
tree | 7829b3138357e23f6fe8cdae7e86d1f581115075 | |
parent | 99a39f6f4a6f944a0cce2505392bf24074db3d98 (diff) | |
download | lua-26d4a7396248623985b59d7e027cfecee561f446.tar.gz lua-26d4a7396248623985b59d7e027cfecee561f446.tar.bz2 lua-26d4a7396248623985b59d7e027cfecee561f446.zip |
with light C functions, 'pairs' does not need to keep 'next' as an
upvalue.
-rw-r--r-- | lbaselib.c | 26 |
1 files changed, 8 insertions, 18 deletions
@@ -1,5 +1,5 @@ | |||
1 | /* | 1 | /* |
2 | ** $Id: lbaselib.c,v 1.240 2010/03/26 20:58:11 roberto Exp roberto $ | 2 | ** $Id: lbaselib.c,v 1.241 2010/04/02 15:19:19 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 | */ |
@@ -182,10 +182,11 @@ static int luaB_type (lua_State *L) { | |||
182 | } | 182 | } |
183 | 183 | ||
184 | 184 | ||
185 | static int pairsmeta (lua_State *L, const char *method, int iszero) { | 185 | static int pairsmeta (lua_State *L, const char *method, int iszero, |
186 | lua_CFunction iter) { | ||
186 | if (!luaL_getmetafield(L, 1, method)) { /* no metamethod? */ | 187 | if (!luaL_getmetafield(L, 1, method)) { /* no metamethod? */ |
187 | luaL_checktype(L, 1, LUA_TTABLE); /* argument must be a table */ | 188 | luaL_checktype(L, 1, LUA_TTABLE); /* argument must be a table */ |
188 | lua_pushvalue(L, lua_upvalueindex(1)); /* will return generator, */ | 189 | lua_pushcfunction(L, iter); /* will return generator, */ |
189 | lua_pushvalue(L, 1); /* state, */ | 190 | lua_pushvalue(L, 1); /* state, */ |
190 | if (iszero) lua_pushinteger(L, 0); /* and initial value */ | 191 | if (iszero) lua_pushinteger(L, 0); /* and initial value */ |
191 | else lua_pushnil(L); | 192 | else lua_pushnil(L); |
@@ -211,7 +212,7 @@ static int luaB_next (lua_State *L) { | |||
211 | 212 | ||
212 | 213 | ||
213 | static int luaB_pairs (lua_State *L) { | 214 | static int luaB_pairs (lua_State *L) { |
214 | return pairsmeta(L, "__pairs", 0); | 215 | return pairsmeta(L, "__pairs", 0, luaB_next); |
215 | } | 216 | } |
216 | 217 | ||
217 | 218 | ||
@@ -228,13 +229,11 @@ static int ipairsaux (lua_State *L) { | |||
228 | 229 | ||
229 | 230 | ||
230 | static int luaB_ipairs (lua_State *L) { | 231 | static int luaB_ipairs (lua_State *L) { |
231 | return pairsmeta(L, "__ipairs", 1); | 232 | return pairsmeta(L, "__ipairs", 1, ipairsaux); |
232 | } | 233 | } |
233 | 234 | ||
234 | #else | 235 | #else |
235 | 236 | ||
236 | #define ipairsaux luaB_ipairs | ||
237 | |||
238 | static int luaB_ipairs (lua_State *L) { | 237 | static int luaB_ipairs (lua_State *L) { |
239 | return luaL_error(L, "'ipairs' deprecated"); | 238 | return luaL_error(L, "'ipairs' deprecated"); |
240 | } | 239 | } |
@@ -485,11 +484,13 @@ static const luaL_Reg base_funcs[] = { | |||
485 | {"gcinfo", luaB_gcinfo}, | 484 | {"gcinfo", luaB_gcinfo}, |
486 | {"getfenv", luaB_getfenv}, | 485 | {"getfenv", luaB_getfenv}, |
487 | {"getmetatable", luaB_getmetatable}, | 486 | {"getmetatable", luaB_getmetatable}, |
487 | {"ipairs", luaB_ipairs}, | ||
488 | {"loadfile", luaB_loadfile}, | 488 | {"loadfile", luaB_loadfile}, |
489 | {"load", luaB_load}, | 489 | {"load", luaB_load}, |
490 | {"loadin", luaB_loadin}, | 490 | {"loadin", luaB_loadin}, |
491 | {"loadstring", luaB_loadstring}, | 491 | {"loadstring", luaB_loadstring}, |
492 | {"next", luaB_next}, | 492 | {"next", luaB_next}, |
493 | {"pairs", luaB_pairs}, | ||
493 | {"pcall", luaB_pcall}, | 494 | {"pcall", luaB_pcall}, |
494 | {"print", luaB_print}, | 495 | {"print", luaB_print}, |
495 | {"rawequal", luaB_rawequal}, | 496 | {"rawequal", luaB_rawequal}, |
@@ -643,14 +644,6 @@ static const luaL_Reg co_funcs[] = { | |||
643 | /* }====================================================== */ | 644 | /* }====================================================== */ |
644 | 645 | ||
645 | 646 | ||
646 | static void auxopen (lua_State *L, const char *name, | ||
647 | lua_CFunction f, lua_CFunction u) { | ||
648 | lua_pushcfunction(L, u); | ||
649 | lua_pushcclosure(L, f, 1); | ||
650 | lua_setfield(L, -2, name); | ||
651 | } | ||
652 | |||
653 | |||
654 | static void base_open (lua_State *L) { | 647 | static void base_open (lua_State *L) { |
655 | /* set global _G */ | 648 | /* set global _G */ |
656 | lua_pushglobaltable(L); | 649 | lua_pushglobaltable(L); |
@@ -660,9 +653,6 @@ static void base_open (lua_State *L) { | |||
660 | luaL_register(L, "_G", base_funcs); | 653 | luaL_register(L, "_G", base_funcs); |
661 | lua_pushliteral(L, LUA_VERSION); | 654 | lua_pushliteral(L, LUA_VERSION); |
662 | lua_setfield(L, -2, "_VERSION"); /* set global _VERSION */ | 655 | lua_setfield(L, -2, "_VERSION"); /* set global _VERSION */ |
663 | /* `ipairs' and `pairs' need auxiliary functions as upvalues */ | ||
664 | auxopen(L, "ipairs", luaB_ipairs, ipairsaux); | ||
665 | auxopen(L, "pairs", luaB_pairs, luaB_next); | ||
666 | /* `newproxy' needs a weaktable as upvalue */ | 656 | /* `newproxy' needs a weaktable as upvalue */ |
667 | lua_createtable(L, 0, 1); /* new table `w' */ | 657 | lua_createtable(L, 0, 1); /* new table `w' */ |
668 | lua_pushvalue(L, -1); /* `w' will be its own metatable */ | 658 | lua_pushvalue(L, -1); /* `w' will be its own metatable */ |