aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRoberto Ierusalimschy <roberto@inf.puc-rio.br>2003-04-07 11:35:00 -0300
committerRoberto Ierusalimschy <roberto@inf.puc-rio.br>2003-04-07 11:35:00 -0300
commitf0cc013afac750ed8ebc79fa3c2413121543ecc7 (patch)
tree11f040fb241ed339834960ce198fa995939fa761
parent0d88545b82b82671904474499b5d312141170ab6 (diff)
downloadlua-f0cc013afac750ed8ebc79fa3c2413121543ecc7.tar.gz
lua-f0cc013afac750ed8ebc79fa3c2413121543ecc7.tar.bz2
lua-f0cc013afac750ed8ebc79fa3c2413121543ecc7.zip
luaL_getn/setn must operate correctly over negative indices
-rw-r--r--lauxlib.c13
1 files changed, 11 insertions, 2 deletions
diff --git a/lauxlib.c b/lauxlib.c
index 6f802534..bb546001 100644
--- a/lauxlib.c
+++ b/lauxlib.c
@@ -1,5 +1,5 @@
1/* 1/*
2** $Id: lauxlib.c,v 1.98 2003/04/01 17:52:31 roberto Exp roberto $ 2** $Id: lauxlib.c,v 1.99 2003/04/03 13:35:34 roberto Exp roberto $
3** Auxiliary functions for building Lua libraries 3** Auxiliary functions for building Lua libraries
4** See Copyright Notice in lua.h 4** See Copyright Notice in lua.h
5*/ 5*/
@@ -31,6 +31,11 @@
31#define ARRAYSIZE_REF 2 /* array sizes */ 31#define ARRAYSIZE_REF 2 /* array sizes */
32 32
33 33
34/* convert a stack index to positive */
35#define abs_index(L, i) ((i) > 0 || (i) <= LUA_REGISTRYINDEX ? (i) : \
36 lua_gettop(L) + (i) + 1)
37
38
34/* 39/*
35** {====================================================== 40** {======================================================
36** Error-report functions 41** Error-report functions
@@ -208,6 +213,7 @@ LUALIB_API int luaL_getmetafield (lua_State *L, int obj, const char *event) {
208 213
209 214
210LUALIB_API int luaL_callmeta (lua_State *L, int obj, const char *event) { 215LUALIB_API int luaL_callmeta (lua_State *L, int obj, const char *event) {
216 obj = abs_index(L, obj);
211 if (!luaL_getmetafield(L, obj, event)) /* no metafield? */ 217 if (!luaL_getmetafield(L, obj, event)) /* no metafield? */
212 return 0; 218 return 0;
213 lua_pushvalue(L, obj); 219 lua_pushvalue(L, obj);
@@ -274,6 +280,7 @@ static void getsizes (lua_State *L) {
274 280
275 281
276void luaL_setn (lua_State *L, int t, int n) { 282void luaL_setn (lua_State *L, int t, int n) {
283 t = abs_index(L, t);
277 lua_pushliteral(L, "n"); 284 lua_pushliteral(L, "n");
278 lua_rawget(L, t); 285 lua_rawget(L, t);
279 if (checkint(L, 1) >= 0) { /* is there a numeric field `n'? */ 286 if (checkint(L, 1) >= 0) { /* is there a numeric field `n'? */
@@ -293,6 +300,7 @@ void luaL_setn (lua_State *L, int t, int n) {
293 300
294int luaL_getn (lua_State *L, int t) { 301int luaL_getn (lua_State *L, int t) {
295 int n; 302 int n;
303 t = abs_index(L, t);
296 lua_pushliteral(L, "n"); /* try t.n */ 304 lua_pushliteral(L, "n"); /* try t.n */
297 lua_rawget(L, t); 305 lua_rawget(L, t);
298 if ((n = checkint(L, 1)) >= 0) return n; 306 if ((n = checkint(L, 1)) >= 0) return n;
@@ -320,7 +328,6 @@ int luaL_getn (lua_State *L, int t) {
320*/ 328*/
321 329
322 330
323#define buffempty(B) ((B)->p == (B)->buffer)
324#define bufflen(B) ((B)->p - (B)->buffer) 331#define bufflen(B) ((B)->p - (B)->buffer)
325#define bufffree(B) ((size_t)(LUAL_BUFFERSIZE - bufflen(B))) 332#define bufffree(B) ((size_t)(LUAL_BUFFERSIZE - bufflen(B)))
326 333
@@ -411,6 +418,7 @@ LUALIB_API void luaL_buffinit (lua_State *L, luaL_Buffer *B) {
411 418
412LUALIB_API int luaL_ref (lua_State *L, int t) { 419LUALIB_API int luaL_ref (lua_State *L, int t) {
413 int ref; 420 int ref;
421 t = abs_index(L, t);
414 if (lua_isnil(L, -1)) { 422 if (lua_isnil(L, -1)) {
415 lua_pop(L, 1); /* remove from stack */ 423 lua_pop(L, 1); /* remove from stack */
416 return LUA_REFNIL; /* `nil' has a unique fixed reference */ 424 return LUA_REFNIL; /* `nil' has a unique fixed reference */
@@ -436,6 +444,7 @@ LUALIB_API int luaL_ref (lua_State *L, int t) {
436 444
437LUALIB_API void luaL_unref (lua_State *L, int t, int ref) { 445LUALIB_API void luaL_unref (lua_State *L, int t, int ref) {
438 if (ref >= 0) { 446 if (ref >= 0) {
447 t = abs_index(L, t);
439 lua_rawgeti(L, t, FREELIST_REF); 448 lua_rawgeti(L, t, FREELIST_REF);
440 lua_rawseti(L, t, ref); /* t[ref] = t[FREELIST_REF] */ 449 lua_rawseti(L, t, ref); /* t[ref] = t[FREELIST_REF] */
441 lua_pushnumber(L, (lua_Number)ref); 450 lua_pushnumber(L, (lua_Number)ref);