Browse Source

first implementation of multiple states (reentrant code).

Roberto Ierusalimschy 26 years ago
parent
commit
29ede6aa13
44 changed files with 2075 additions and 1930 deletions
  1. 187 187
      lapi.c
  2. 6 7
      lapi.h
  3. 38 37
      lauxlib.c
  4. 63 22
      lauxlib.h
  5. 18 17
      lbuffer.c
  6. 295 296
      lbuiltin.c
  7. 3 2
      lbuiltin.h
  8. 94 92
      ldblib.c
  9. 64 63
      ldo.c
  10. 14 14
      ldo.h
  11. 20 18
      lfunc.c
  12. 5 5
      lfunc.h
  13. 62 61
      lgc.c
  14. 3 3
      lgc.h
  15. 8 6
      linit.c
  16. 182 180
      liolib.c
  17. 77 74
      llex.c
  18. 4 3
      llex.h
  19. 73 71
      lmathlib.c
  20. 13 11
      lmem.c
  21. 12 10
      lmem.h
  22. 6 4
      lobject.c
  23. 10 10
      lobject.h
  24. 61 56
      lparser.c
  25. 2 5
      lparser.h
  26. 14 12
      lref.c
  27. 4 4
      lref.h
  28. 27 25
      lstate.c
  29. 2 2
      lstate.h
  30. 48 46
      lstring.c
  31. 13 13
      lstring.h
  32. 156 154
      lstrlib.c
  33. 41 39
      ltable.c
  34. 14 14
      ltable.h
  35. 34 32
      ltm.c
  36. 8 8
      ltm.h
  37. 8 9
      lua.c
  38. 145 90
      lua.h
  39. 13 13
      luadebug.h
  40. 21 12
      lualib.h
  41. 77 75
      lundump.c
  42. 4 4
      lundump.h
  43. 113 111
      lvm.c
  44. 13 13
      lvm.h

+ 187 - 187
lapi.c

@@ -1,5 +1,5 @@
 /*
-** $Id: lapi.c,v 1.55 1999/11/04 17:22:26 roberto Exp roberto $
+** $Id: lapi.c,v 1.56 1999/11/11 17:02:40 roberto Exp roberto $
 ** Lua API
 ** See Copyright Notice in lua.h
 */
@@ -7,6 +7,8 @@
 
 #include <string.h>
 
+#define LUA_REENTRANT
+
 #include "lapi.h"
 #include "lauxlib.h"
 #include "ldo.h"
@@ -29,8 +31,8 @@ const char lua_ident[] = "$Lua: " LUA_VERSION " " LUA_COPYRIGHT " $\n"
 
 
 
-TObject *luaA_Address (lua_Object o) {
-  return (o != LUA_NOOBJECT) ?  Address(o) : NULL;
+TObject *luaA_Address (lua_State *L, lua_Object o) {
+  return (o != LUA_NOOBJECT) ?  Address(L, o) : NULL;
 }
 
 
@@ -60,27 +62,27 @@ static const TObject *luaA_protovalue (const TObject *o) {
 }
 
 
-static void checkCparams (int nParams) {
+static void checkCparams (lua_State *L, int nParams) {
   if (L->stack.top-L->stack.stack < L->Cstack.base+nParams)
-    lua_error("API error - wrong number of arguments in C2lua stack");
+    lua_error(L, "API error - wrong number of arguments in C2lua stack");
 }
 
 
-static lua_Object put_luaObject (const TObject *o) {
-  luaD_openstack((L->stack.top-L->stack.stack)-L->Cstack.base);
+static lua_Object put_luaObject (lua_State *L, const TObject *o) {
+  luaD_openstack(L, (L->stack.top-L->stack.stack)-L->Cstack.base);
   L->stack.stack[L->Cstack.base++] = *o;
   return L->Cstack.base;  /* this is +1 real position (see Ref) */
 }
 
 
-lua_Object luaA_putObjectOnTop (void) {
-  luaD_openstack((L->stack.top-L->stack.stack)-L->Cstack.base);
+lua_Object luaA_putObjectOnTop (lua_State *L) {
+  luaD_openstack(L, (L->stack.top-L->stack.stack)-L->Cstack.base);
   L->stack.stack[L->Cstack.base++] = *(--L->stack.top);
   return L->Cstack.base;  /* this is +1 real position (see Ref) */
 }
 
 
-static void top2LC (int n) {
+static void top2LC (lua_State *L, int n) {
   /* Put the 'n' elements on the top as the Lua2C contents */
   L->Cstack.base = (L->stack.top-L->stack.stack);  /* new base */
   L->Cstack.lua2C = L->Cstack.base-n;  /* position of the new results */
@@ -88,9 +90,9 @@ static void top2LC (int n) {
 }
 
 
-lua_Object lua_pop (void) {
-  checkCparams(1);
-  return luaA_putObjectOnTop();
+lua_Object lua_pop (lua_State *L) {
+  checkCparams(L, 1);
+  return luaA_putObjectOnTop(L);
 }
 
 
@@ -98,248 +100,248 @@ lua_Object lua_pop (void) {
 ** Get a parameter, returning the object handle or LUA_NOOBJECT on error.
 ** 'number' must be 1 to get the first parameter.
 */
-lua_Object lua_lua2C (int number) {
+lua_Object lua_lua2C (lua_State *L, int number) {
   if (number <= 0 || number > L->Cstack.num) return LUA_NOOBJECT;
-  /* Ref(L->stack.stack+(L->Cstack.lua2C+number-1)) ==
+  /* Ref(L, L->stack.stack+(L->Cstack.lua2C+number-1)) ==
      L->stack.stack+(L->Cstack.lua2C+number-1)-L->stack.stack+1 == */
   return L->Cstack.lua2C+number;
 }
 
 
-int lua_callfunction (lua_Object function) {
+int lua_callfunction (lua_State *L, lua_Object function) {
   if (function == LUA_NOOBJECT)
     return 1;
   else {
-    luaD_openstack((L->stack.top-L->stack.stack)-L->Cstack.base);
-    set_normalized(L->stack.stack+L->Cstack.base, Address(function));
-    return luaD_protectedrun();
+    luaD_openstack(L, (L->stack.top-L->stack.stack)-L->Cstack.base);
+    set_normalized(L->stack.stack+L->Cstack.base, Address(L, function));
+    return luaD_protectedrun(L);
   }
 }
 
 
-lua_Object lua_gettagmethod (int tag, const char *event) {
-  return put_luaObject(luaT_gettagmethod(tag, event));
+lua_Object lua_gettagmethod (lua_State *L, int tag, const char *event) {
+  return put_luaObject(L, luaT_gettagmethod(L, tag, event));
 }
 
 
-lua_Object lua_settagmethod (int tag, const char *event) {
-  checkCparams(1);
-  luaT_settagmethod(tag, event, L->stack.top-1);
-  return luaA_putObjectOnTop();
+lua_Object lua_settagmethod (lua_State *L, int tag, const char *event) {
+  checkCparams(L, 1);
+  luaT_settagmethod(L, tag, event, L->stack.top-1);
+  return luaA_putObjectOnTop(L);
 }
 
 
-lua_Object lua_seterrormethod (void) {
+lua_Object lua_seterrormethod (lua_State *L) {
   lua_Object temp;
-  checkCparams(1);
-  temp = lua_getglobal("_ERRORMESSAGE");
-  lua_setglobal("_ERRORMESSAGE");
+  checkCparams(L, 1);
+  temp = lua_getglobal(L, "_ERRORMESSAGE");
+  lua_setglobal(L, "_ERRORMESSAGE");
   return temp;
 }
 
 
-lua_Object lua_gettable (void) {
-  checkCparams(2);
-  luaV_gettable();
-  return luaA_putObjectOnTop();
+lua_Object lua_gettable (lua_State *L) {
+  checkCparams(L, 2);
+  luaV_gettable(L);
+  return luaA_putObjectOnTop(L);
 }
 
 
-lua_Object lua_rawgettable (void) {
-  checkCparams(2);
+lua_Object lua_rawgettable (lua_State *L) {
+  checkCparams(L, 2);
   if (ttype(L->stack.top-2) != LUA_T_ARRAY)
-    lua_error("indexed expression not a table in rawgettable");
-  *(L->stack.top-2) = *luaH_get(avalue(L->stack.top-2), L->stack.top-1);
+    lua_error(L, "indexed expression not a table in rawgettable");
+  *(L->stack.top-2) = *luaH_get(L, avalue(L->stack.top-2), L->stack.top-1);
   --L->stack.top;
-  return luaA_putObjectOnTop();
+  return luaA_putObjectOnTop(L);
 }
 
 
-void lua_settable (void) {
-  checkCparams(3);
-  luaV_settable(L->stack.top-3);
+void lua_settable (lua_State *L) {
+  checkCparams(L, 3);
+  luaV_settable(L, L->stack.top-3);
   L->stack.top -= 2;  /* pop table and index */
 }
 
 
-void lua_rawsettable (void) {
-  checkCparams(3);
-  luaV_rawsettable(L->stack.top-3);
+void lua_rawsettable (lua_State *L) {
+  checkCparams(L, 3);
+  luaV_rawsettable(L, L->stack.top-3);
 }
 
 
-lua_Object lua_createtable (void) {
+lua_Object lua_createtable (lua_State *L) {
   TObject o;
-  luaC_checkGC();
-  avalue(&o) = luaH_new(0);
+  luaC_checkGC(L);
+  avalue(&o) = luaH_new(L, 0);
   ttype(&o) = LUA_T_ARRAY;
-  return put_luaObject(&o);
+  return put_luaObject(L, &o);
 }
 
 
-lua_Object lua_getglobal (const char *name) {
-  luaD_checkstack(2);  /* may need that to call T.M. */
-  luaV_getglobal(luaS_assertglobalbyname(name));
-  return luaA_putObjectOnTop();
+lua_Object lua_getglobal (lua_State *L, const char *name) {
+  luaD_checkstack(L, 2);  /* may need that to call T.M. */
+  luaV_getglobal(L, luaS_assertglobalbyname(L, name));
+  return luaA_putObjectOnTop(L);
 }
 
 
-lua_Object lua_rawgetglobal (const char *name) {
-  GlobalVar *gv = luaS_assertglobalbyname(name);
-  return put_luaObject(&gv->value);
+lua_Object lua_rawgetglobal (lua_State *L, const char *name) {
+  GlobalVar *gv = luaS_assertglobalbyname(L, name);
+  return put_luaObject(L, &gv->value);
 }
 
 
-void lua_setglobal (const char *name) {
-  checkCparams(1);
-  luaD_checkstack(2);  /* may need that to call T.M. */
-  luaV_setglobal(luaS_assertglobalbyname(name));
+void lua_setglobal (lua_State *L, const char *name) {
+  checkCparams(L, 1);
+  luaD_checkstack(L, 2);  /* may need that to call T.M. */
+  luaV_setglobal(L, luaS_assertglobalbyname(L, name));
 }
 
 
-void lua_rawsetglobal (const char *name) {
-  GlobalVar *gv = luaS_assertglobalbyname(name);
-  checkCparams(1);
+void lua_rawsetglobal (lua_State *L, const char *name) {
+  GlobalVar *gv = luaS_assertglobalbyname(L, name);
+  checkCparams(L, 1);
   gv->value = *(--L->stack.top);
 }
 
 
-const char *lua_type (lua_Object o) {
-  return (o == LUA_NOOBJECT) ? "NOOBJECT" : luaO_typename(Address(o));
+const char *lua_type (lua_State *L, lua_Object o) {
+  return (o == LUA_NOOBJECT) ? "NOOBJECT" : luaO_typename(L, Address(L, o));
 }
 
-int lua_isnil (lua_Object o) {
-  return (o != LUA_NOOBJECT) && (ttype(Address(o)) == LUA_T_NIL);
+int lua_isnil (lua_State *L, lua_Object o) {
+  return (o != LUA_NOOBJECT) && (ttype(Address(L, o)) == LUA_T_NIL);
 }
 
-int lua_istable (lua_Object o) {
-  return (o != LUA_NOOBJECT) && (ttype(Address(o)) == LUA_T_ARRAY);
+int lua_istable (lua_State *L, lua_Object o) {
+  return (o != LUA_NOOBJECT) && (ttype(Address(L, o)) == LUA_T_ARRAY);
 }
 
-int lua_isuserdata (lua_Object o) {
-  return (o != LUA_NOOBJECT) && (ttype(Address(o)) == LUA_T_USERDATA);
+int lua_isuserdata (lua_State *L, lua_Object o) {
+  return (o != LUA_NOOBJECT) && (ttype(Address(L, o)) == LUA_T_USERDATA);
 }
 
-int lua_iscfunction (lua_Object o) {
-  return (lua_tag(o) == LUA_T_CPROTO);
+int lua_iscfunction (lua_State *L, lua_Object o) {
+  return (lua_tag(L, o) == LUA_T_CPROTO);
 }
 
-int lua_isnumber (lua_Object o) {
-  return (o != LUA_NOOBJECT) && (tonumber(Address(o)) == 0);
+int lua_isnumber (lua_State *L, lua_Object o) {
+  return (o != LUA_NOOBJECT) && (tonumber(Address(L, o)) == 0);
 }
 
-int lua_isstring (lua_Object o) {
-  int t = lua_tag(o);
+int lua_isstring (lua_State *L, lua_Object o) {
+  int t = lua_tag(L, o);
   return (t == LUA_T_STRING) || (t == LUA_T_NUMBER);
 }
 
-int lua_isfunction (lua_Object o) {
-  int t = lua_tag(o);
+int lua_isfunction (lua_State *L, lua_Object o) {
+  int t = lua_tag(L, o);
   return (t == LUA_T_PROTO) || (t == LUA_T_CPROTO);
 }
 
-int lua_equalobj (lua_Object o1, lua_Object o2) {
+int lua_equalobj (lua_State *L, lua_Object o1, lua_Object o2) {
   if (o1 == LUA_NOOBJECT || o2 == LUA_NOOBJECT) return 0;
-  else return luaO_equalObj(Address(o1), Address(o2));
+  else return luaO_equalObj(Address(L, o1), Address(L, o2));
 }
 
 
-double lua_getnumber (lua_Object object) {
+double lua_getnumber (lua_State *L, lua_Object object) {
  if (object == LUA_NOOBJECT) return 0.0;
- if (tonumber(Address(object))) return 0.0;
- else return (nvalue(Address(object)));
+ if (tonumber(Address(L, object))) return 0.0;
+ else return (nvalue(Address(L, object)));
 }
 
-const char *lua_getstring (lua_Object object) {
-  luaC_checkGC();  /* "tostring" may create a new string */
-  if (object == LUA_NOOBJECT || tostring(Address(object)))
+const char *lua_getstring (lua_State *L, lua_Object object) {
+  luaC_checkGC(L);  /* `tostring' may create a new string */
+  if (object == LUA_NOOBJECT || tostring(L, Address(L, object)))
     return NULL;
-  else return (svalue(Address(object)));
+  else return (svalue(Address(L, object)));
 }
 
-long lua_strlen (lua_Object object) {
-  luaC_checkGC();  /* "tostring" may create a new string */
-  if (object == LUA_NOOBJECT || tostring(Address(object)))
+long lua_strlen (lua_State *L, lua_Object object) {
+  luaC_checkGC(L);  /* `tostring' may create a new string */
+  if (object == LUA_NOOBJECT || tostring(L, Address(L, object)))
     return 0L;
-  else return (tsvalue(Address(object))->u.s.len);
+  else return (tsvalue(Address(L, object))->u.s.len);
 }
 
-void *lua_getuserdata (lua_Object object) {
-  if (object == LUA_NOOBJECT || ttype(Address(object)) != LUA_T_USERDATA)
+void *lua_getuserdata (lua_State *L, lua_Object object) {
+  if (object == LUA_NOOBJECT || ttype(Address(L, object)) != LUA_T_USERDATA)
     return NULL;
-  else return tsvalue(Address(object))->u.d.value;
+  else return tsvalue(Address(L, object))->u.d.value;
 }
 
-lua_CFunction lua_getcfunction (lua_Object object) {
-  if (!lua_iscfunction(object))
+lua_CFunction lua_getcfunction (lua_State *L, lua_Object object) {
+  if (!lua_iscfunction(L, object))
     return NULL;
-  else return fvalue(luaA_protovalue(Address(object)));
+  else return fvalue(luaA_protovalue(Address(L, object)));
 }
 
 
-void lua_pushnil (void) {
+void lua_pushnil (lua_State *L) {
   ttype(L->stack.top) = LUA_T_NIL;
   incr_top;
 }
 
-void lua_pushnumber (double n) {
+void lua_pushnumber (lua_State *L, double n) {
   ttype(L->stack.top) = LUA_T_NUMBER;
   nvalue(L->stack.top) = n;
   incr_top;
 }
 
-void lua_pushlstring (const char *s, long len) {
-  tsvalue(L->stack.top) = luaS_newlstr(s, len);
+void lua_pushlstring (lua_State *L, const char *s, long len) {
+  tsvalue(L->stack.top) = luaS_newlstr(L, s, len);
   ttype(L->stack.top) = LUA_T_STRING;
   incr_top;
-  luaC_checkGC();
+  luaC_checkGC(L);
 }
 
-void lua_pushstring (const char *s) {
+void lua_pushstring (lua_State *L, const char *s) {
   if (s == NULL)
-    lua_pushnil();
+    lua_pushnil(L);
   else
-    lua_pushlstring(s, strlen(s));
+    lua_pushlstring(L, s, strlen(s));
 }
 
-void lua_pushcclosure (lua_CFunction fn, int n) {
+void lua_pushcclosure (lua_State *L, lua_CFunction fn, int n) {
   if (fn == NULL)
-    lua_error("API error - attempt to push a NULL Cfunction");
-  checkCparams(n);
+    lua_error(L, "API error - attempt to push a NULL Cfunction");
+  checkCparams(L, n);
   ttype(L->stack.top) = LUA_T_CPROTO;
   fvalue(L->stack.top) = fn;
   incr_top;
-  luaV_closure(n);
-  luaC_checkGC();
+  luaV_closure(L, n);
+  luaC_checkGC(L);
 }
 
-void lua_pushusertag (void *u, int tag) {
+void lua_pushusertag (lua_State *L, void *u, int tag) {
   if (tag < 0 && tag != LUA_ANYTAG)
-    luaT_realtag(tag);  /* error if tag is not valid */
-  tsvalue(L->stack.top) = luaS_createudata(u, tag);
+    luaT_realtag(L, tag);  /* error if tag is not valid */
+  tsvalue(L->stack.top) = luaS_createudata(L, u, tag);
   ttype(L->stack.top) = LUA_T_USERDATA;
   incr_top;
-  luaC_checkGC();
+  luaC_checkGC(L);
 }
 
-void luaA_pushobject (const TObject *o) {
+void luaA_pushobject (lua_State *L, const TObject *o) {
   *L->stack.top = *o;
   incr_top;
 }
 
-void lua_pushobject (lua_Object o) {
+void lua_pushobject (lua_State *L, lua_Object o) {
   if (o == LUA_NOOBJECT)
-    lua_error("API error - attempt to push a NOOBJECT");
-  set_normalized(L->stack.top, Address(o));
+    lua_error(L, "API error - attempt to push a NOOBJECT");
+  set_normalized(L->stack.top, Address(L, o));
   incr_top;
 }
 
 
-int lua_tag (lua_Object lo) {
+int lua_tag (lua_State *L, lua_Object lo) {
   if (lo == LUA_NOOBJECT)
      return LUA_T_NIL;
   else {
-    const TObject *o = Address(lo);
+    const TObject *o = Address(L, lo);
     int t;
     switch (t = ttype(o)) {
       case LUA_T_USERDATA:
@@ -354,7 +356,7 @@ int lua_tag (lua_Object lo) {
         return o->value.cl->consts[0].ttype;
 #ifdef DEBUG
       case LUA_T_LINE:
-        LUA_INTERNALERROR("invalid type");
+        LUA_INTERNALERROR(L, "invalid type");
 #endif
       default:
         return t;
@@ -363,9 +365,9 @@ int lua_tag (lua_Object lo) {
 }
 
 
-void lua_settag (int tag) {
-  checkCparams(1);
-  luaT_realtag(tag);
+void lua_settag (lua_State *L, int tag) {
+  checkCparams(L, 1);
+  luaT_realtag(L, tag);
   switch (ttype(L->stack.top-1)) {
     case LUA_T_ARRAY:
       (L->stack.top-1)->value.a->htag = tag;
@@ -374,20 +376,20 @@ void lua_settag (int tag) {
       (L->stack.top-1)->value.ts->u.d.tag = tag;
       break;
     default:
-      luaL_verror("cannot change the tag of a %.20s",
-                  luaO_typename(L->stack.top-1));
+      luaL_verror(L, "cannot change the tag of a %.20s",
+                  luaO_typename(L, L->stack.top-1));
   }
   L->stack.top--;
 }
 
 
-GlobalVar *luaA_nextvar (TaggedString *ts) {
+GlobalVar *luaA_nextvar (lua_State *L, TaggedString *ts) {
   GlobalVar *gv;
   if (ts == NULL)
     gv = L->rootglobal;  /* first variable */
   else {
     /* check whether name is in global var list */
-    luaL_arg_check(ts->u.s.gv, 1, "variable name expected");
+    luaL_arg_check(L, ts->u.s.gv, 1, "variable name expected");
     gv = ts->u.s.gv->next;  /* get next */
   }
   while (gv && gv->value.ttype == LUA_T_NIL)  /* skip globals with nil */
@@ -395,33 +397,33 @@ GlobalVar *luaA_nextvar (TaggedString *ts) {
   if (gv) {
     ttype(L->stack.top) = LUA_T_STRING; tsvalue(L->stack.top) = gv->name;
     incr_top;
-    luaA_pushobject(&gv->value);
+    luaA_pushobject(L, &gv->value);
   }
   return gv;
 }
 
 
-const char *lua_nextvar (const char *varname) {
-  TaggedString *ts = (varname == NULL) ? NULL : luaS_new(varname);
-  GlobalVar *gv = luaA_nextvar(ts);
+const char *lua_nextvar (lua_State *L, const char *varname) {
+  TaggedString *ts = (varname == NULL) ? NULL : luaS_new(L, varname);
+  GlobalVar *gv = luaA_nextvar(L, ts);
   if (gv) {
-    top2LC(2);
+    top2LC(L, 2);
     return gv->name->str;
   }
   else {
-    top2LC(0);
+    top2LC(L, 0);
     return NULL;
   }
 }
 
 
-int luaA_next (const Hash *t, int i) {
+int luaA_next (lua_State *L, const Hash *t, int i) {
   int tsize = t->size;
   for (; i<tsize; i++) {
-    Node *n = node(t, i);
-    if (ttype(val(n)) != LUA_T_NIL) {
-      luaA_pushobject(key(n));
-      luaA_pushobject(val(n));
+    Node *n = node(L, t, i);
+    if (ttype(val(L, n)) != LUA_T_NIL) {
+      luaA_pushobject(L, key(L, n));
+      luaA_pushobject(L, val(L, n));
       return i+1;  /* index to be used next time */
     }
   }
@@ -429,12 +431,12 @@ int luaA_next (const Hash *t, int i) {
 }
 
 
-int lua_next (lua_Object o, int i) {
-  const TObject *t = Address(o);
+int lua_next (lua_State *L, lua_Object o, int i) {
+  const TObject *t = Address(L, o);
   if (ttype(t) != LUA_T_ARRAY)
-    lua_error("API error - object is not a table in `lua_next'"); 
-  i = luaA_next(avalue(t), i);
-  top2LC((i==0) ? 0 : 2);
+    lua_error(L, "API error - object is not a table in `lua_next'"); 
+  i = luaA_next(L, avalue(t), i);
+  top2LC(L, (i==0) ? 0 : 2);
   return i;
 }
 
@@ -446,25 +448,21 @@ int lua_next (lua_Object o, int i) {
 ** =======================================================
 */
 
-lua_State *lua_setstate (lua_State *st) {
-  lua_State *old = lua_state;
-  lua_state = st;
-  return old;
-}
 
-lua_LHFunction lua_setlinehook (lua_LHFunction func) {
+
+lua_LHFunction lua_setlinehook (lua_State *L, lua_LHFunction func) {
   lua_LHFunction old = L->linehook;
   L->linehook = func;
   return old;
 }
 
-lua_CHFunction lua_setcallhook (lua_CHFunction func) {
+lua_CHFunction lua_setcallhook (lua_State *L, lua_CHFunction func) {
   lua_CHFunction old = L->callhook;
   L->callhook = func;
   return old;
 }
 
-int lua_setdebug (int debug) {
+int lua_setdebug (lua_State *L, int debug) {
   int old = L->debug;
   L->debug = debug;
   return old;
@@ -480,44 +478,44 @@ int lua_setdebug (int debug) {
 */
 
 
-lua_Function lua_stackedfunction (int level) {
+lua_Function lua_stackedfunction (lua_State *L, int level) {
   StkId i;
   for (i = (L->stack.top-1)-L->stack.stack; i>=0; i--) {
     int t = L->stack.stack[i].ttype;
     if (t == LUA_T_CLMARK || t == LUA_T_PMARK || t == LUA_T_CMARK)
       if (level-- == 0)
-        return Ref(L->stack.stack+i);
+        return Ref(L, L->stack.stack+i);
   }
   return LUA_NOOBJECT;
 }
 
 
-int lua_nups (lua_Function func) {
-  const TObject *o = luaA_Address(func);
+int lua_nups (lua_State *L, lua_Function func) {
+  const TObject *o = luaA_Address(L, func);
   return (!o || normalized_type(o) != LUA_T_CLOSURE) ? 0 : o->value.cl->nelems;
 }
 
 
-int lua_currentline (lua_Function func) {
-  const TObject *f = Address(func);
+int lua_currentline (lua_State *L, lua_Function func) {
+  const TObject *f = Address(L, func);
   return (f+1 < L->stack.top && (f+1)->ttype == LUA_T_LINE) ?
              (f+1)->value.i : -1;
 }
 
 
-lua_Object lua_getlocal (lua_Function func, int local_number,
+lua_Object lua_getlocal (lua_State *L, lua_Function func, int local_number,
                          const char **name) {
   /* check whether func is a Lua function */
-  if (lua_tag(func) != LUA_T_PROTO)
+  if (lua_tag(L, func) != LUA_T_PROTO)
     return LUA_NOOBJECT;
   else {
-    TObject *f = Address(func);
+    TObject *f = Address(L, func);
     TProtoFunc *fp = luaA_protovalue(f)->value.tf;
-    *name = luaF_getlocalname(fp, local_number, lua_currentline(func));
+    *name = luaF_getlocalname(fp, local_number, lua_currentline(L, func));
     if (*name) {
       /* if "*name", there must be a LUA_T_LINE */
       /* therefore, f+2 points to function base */
-      return put_luaObject((f+2)+(local_number-1));
+      return put_luaObject(L, (f+2)+(local_number-1));
     }
     else
       return LUA_NOOBJECT;
@@ -525,15 +523,16 @@ lua_Object lua_getlocal (lua_Function func, int local_number,
 }
 
 
-int lua_setlocal (lua_Function func, int local_number) {
+int lua_setlocal (lua_State *L, lua_Function func, int local_number) {
   /* check whether func is a Lua function */
-  if (lua_tag(func) != LUA_T_PROTO)
+  if (lua_tag(L, func) != LUA_T_PROTO)
     return 0;
   else {
-    TObject *f = Address(func);
+    TObject *f = Address(L, func);
     TProtoFunc *fp = luaA_protovalue(f)->value.tf;
-    const char *name = luaF_getlocalname(fp, local_number, lua_currentline(func));
-    checkCparams(1);
+    const char *name = luaF_getlocalname(fp, local_number,
+                                         lua_currentline(L, func));
+    checkCparams(L, 1);
     --L->stack.top;
     if (name) {
       /* if "name", there must be a LUA_T_LINE */
@@ -547,11 +546,12 @@ int lua_setlocal (lua_Function func, int local_number) {
 }
 
 
-void lua_funcinfo (lua_Object func, const char **source, int *linedefined) {
-  if (!lua_isfunction(func))
-    lua_error("API error - `funcinfo' called with a non-function value");
+void lua_funcinfo (lua_State *L, lua_Object func,
+                   const char **source, int *linedefined) {
+  if (!lua_isfunction(L, func))
+    lua_error(L, "API error - `funcinfo' called with a non-function value");
   else {
-    const TObject *f = luaA_protovalue(Address(func));
+    const TObject *f = luaA_protovalue(Address(L, func));
     if (normalized_type(f) == LUA_T_PROTO) {
       *source = tfvalue(f)->source->str;
       *linedefined = tfvalue(f)->lineDefined;
@@ -564,23 +564,23 @@ void lua_funcinfo (lua_Object func, const char **source, int *linedefined) {
 }
 
 
-static int checkfunc (TObject *o) {
+static int checkfunc (lua_State *L, TObject *o) {
   return luaO_equalObj(o, L->stack.top);
 }
 
 
-const char *lua_getobjname (lua_Object o, const char **name) {
+const char *lua_getobjname (lua_State *L, lua_Object o, const char **name) {
   /* try to find a name for given function */
   GlobalVar *g;
-  set_normalized(L->stack.top, Address(o)); /* to be accessed by "checkfunc" */
+  set_normalized(L->stack.top, Address(L, o)); /* to be used by `checkfunc' */
   for (g=L->rootglobal; g; g=g->next) {
-    if (checkfunc(&g->value)) {
+    if (checkfunc(L, &g->value)) {
       *name = g->name->str;
       return "global";
     }
   }
   /* not found: try tag methods */
-  if ((*name = luaT_travtagmethods(checkfunc)) != NULL)
+  if ((*name = luaT_travtagmethods(L, checkfunc)) != NULL)
     return "tag-method";
   else return "";  /* not found at all */
 }
@@ -600,34 +600,34 @@ const char *lua_getobjname (lua_Object o, const char **name) {
 #endif
 
 
-void lua_beginblock (void) {
-  luaM_growvector(L->Cblocks, L->numCblocks, 1, struct C_Lua_Stack,
+void lua_beginblock (lua_State *L) {
+  luaM_growvector(L, L->Cblocks, L->numCblocks, 1, struct C_Lua_Stack,
                   "too many nested blocks", MAX_C_BLOCKS);
   L->Cblocks[L->numCblocks] = L->Cstack;
   L->numCblocks++;
 }
 
-void lua_endblock (void) {
+void lua_endblock (lua_State *L) {
   --L->numCblocks;
   L->Cstack = L->Cblocks[L->numCblocks];
-  luaD_adjusttop(L->Cstack.base);
+  luaD_adjusttop(L, L->Cstack.base);
 }
 
 
 
-int lua_ref (int lock) {
+int lua_ref (lua_State *L, int lock) {
   int ref;
-  checkCparams(1);
-  ref = luaR_ref(L->stack.top-1, lock);
+  checkCparams(L, 1);
+  ref = luaR_ref(L, L->stack.top-1, lock);
   L->stack.top--;
   return ref;
 }
 
 
 
-lua_Object lua_getref (int ref) {
-  const TObject *o = luaR_getref(ref);
-  return (o ? put_luaObject(o) : LUA_NOOBJECT);
+lua_Object lua_getref (lua_State *L, int ref) {
+  const TObject *o = luaR_getref(L, ref);
+  return (o ? put_luaObject(L, o) : LUA_NOOBJECT);
 }
 
 /* }====================================================== */

+ 6 - 7
lapi.h

@@ -1,5 +1,5 @@
 /*
-** $Id: lapi.h,v 1.7 1999/09/21 16:10:13 roberto Exp roberto $
+** $Id: lapi.h,v 1.8 1999/11/04 17:22:26 roberto Exp roberto $
 ** Auxiliary functions from Lua API
 ** See Copyright Notice in lua.h
 */
@@ -8,14 +8,13 @@
 #define lapi_h
 
 
-#include "lua.h"
 #include "lobject.h"
 
 
-TObject *luaA_Address (lua_Object o);
-void luaA_pushobject (const TObject *o);
-GlobalVar *luaA_nextvar (TaggedString *g);
-int luaA_next (const Hash *t, int i);
-lua_Object luaA_putObjectOnTop (void);
+TObject *luaA_Address (lua_State *L, lua_Object o);
+void luaA_pushobject (lua_State *L, const TObject *o);
+GlobalVar *luaA_nextvar (lua_State *L, TaggedString *g);
+int luaA_next (lua_State *L, const Hash *t, int i);
+lua_Object luaA_putObjectOnTop (lua_State *L);
 
 #endif

+ 38 - 37
lauxlib.c

@@ -1,5 +1,5 @@
 /*
-** $Id: lauxlib.c,v 1.19 1999/09/06 13:13:03 roberto Exp roberto $
+** $Id: lauxlib.c,v 1.20 1999/10/05 18:33:43 roberto Exp roberto $
 ** Auxiliary functions for building Lua libraries
 ** See Copyright Notice in lua.h
 */
@@ -14,6 +14,8 @@
 ** With care, these functions can be used by other libraries.
 */
 
+#define LUA_REENTRANT
+
 #include "lauxlib.h"
 #include "lua.h"
 #include "luadebug.h"
@@ -28,87 +30,86 @@ int luaL_findstring (const char *name, const char *const list[]) {
   return -1;  /* name not found */
 }
 
-void luaL_argerror (int numarg, const char *extramsg) {
-  lua_Function f = lua_stackedfunction(0);
+void luaL_argerror (lua_State *L, int numarg, const char *extramsg) {
+  lua_Function f = lua_stackedfunction(L, 0);
   const char *funcname;
-  lua_getobjname(f, &funcname);
-  numarg -= lua_nups(f);
+  lua_getobjname(L, f, &funcname);
+  numarg -= lua_nups(L, f);
   if (funcname == NULL)
     funcname = "?";
-  luaL_verror("bad argument #%d to function `%.50s' (%.100s)",
+  luaL_verror(L, "bad argument #%d to function `%.50s' (%.100s)",
               numarg, funcname, extramsg);
 }
 
-static const char *checkstr (lua_Object o, int numArg, long *len) {
-  const char *s = lua_getstring(o);
-  luaL_arg_check(s, numArg, "string expected");
-  if (len) *len = lua_strlen(o);
+static const char *checkstr (lua_State *L, lua_Object o, int n, long *len) {
+  const char *s = lua_getstring(L, o);
+  luaL_arg_check(L, s, n, "string expected");
+  if (len) *len = lua_strlen(L, o);
   return s;
 }
 
-const char *luaL_check_lstr (int numArg, long *len) {
-  return checkstr(lua_getparam(numArg), numArg, len);
+const char *luaL_check_lstr (lua_State *L, int n, long *len) {
+  return checkstr(L, lua_getparam(L, n), n, len);
 }
 
-const char *luaL_opt_lstr (int numArg, const char *def, long *len) {
-  lua_Object o = lua_getparam(numArg);
+const char *luaL_opt_lstr (lua_State *L, int n, const char *def, long *len) {
+  lua_Object o = lua_getparam(L, n);
   if (o == LUA_NOOBJECT) {
     if (len) *len = def ? strlen(def) : 0;
     return def;
   }
-  else return checkstr(o, numArg, len);
+  else return checkstr(L, o, n, len);
 }
 
-double luaL_check_number (int numArg) {
-  lua_Object o = lua_getparam(numArg);
-  luaL_arg_check(lua_isnumber(o), numArg, "number expected");
-  return lua_getnumber(o);
+double luaL_check_number (lua_State *L, int n) {
+  lua_Object o = lua_getparam(L, n);
+  luaL_arg_check(L, lua_isnumber(L, o), n, "number expected");
+  return lua_getnumber(L, o);
 }
 
 
-double luaL_opt_number (int numArg, double def) {
-  lua_Object o = lua_getparam(numArg);
+double luaL_opt_number (lua_State *L, int n, double def) {
+  lua_Object o = lua_getparam(L, n);
   if (o == LUA_NOOBJECT) return def;
   else {
-    luaL_arg_check(lua_isnumber(o), numArg, "number expected");
-    return lua_getnumber(o);
+    luaL_arg_check(L, lua_isnumber(L, o), n, "number expected");
+    return lua_getnumber(L, o);
   }
 }
 
 
-lua_Object luaL_tablearg (int arg) {
-  lua_Object o = lua_getparam(arg);
-  luaL_arg_check(lua_istable(o), arg, "table expected");
+lua_Object luaL_tablearg (lua_State *L, int arg) {
+  lua_Object o = lua_getparam(L, arg);
+  luaL_arg_check(L, lua_istable(L, o), arg, "table expected");
   return o;
 }
 
-lua_Object luaL_functionarg (int arg) {
-  lua_Object o = lua_getparam(arg);
-  luaL_arg_check(lua_isfunction(o), arg, "function expected");
+lua_Object luaL_functionarg (lua_State *L, int arg) {
+  lua_Object o = lua_getparam(L, arg);
+  luaL_arg_check(L, lua_isfunction(L, o), arg, "function expected");
   return o;
 }
 
-lua_Object luaL_nonnullarg (int numArg) {
-  lua_Object o = lua_getparam(numArg);
-  luaL_arg_check(o != LUA_NOOBJECT, numArg, "value expected");
+lua_Object luaL_nonnullarg (lua_State *L, int n) {
+  lua_Object o = lua_getparam(L, n);
+  luaL_arg_check(L, o != LUA_NOOBJECT, n, "value expected");
   return o;
 }
 
-void luaL_openlib (const struct luaL_reg *l, int n) {
+void luaL_openlib (lua_State *L, const struct luaL_reg *l, int n) {
   int i;
-  lua_open();  /* make sure lua is already open */
   for (i=0; i<n; i++)
-    lua_register(l[i].name, l[i].func);
+    lua_register(L, l[i].name, l[i].func);
 }
 
 
-void luaL_verror (const char *fmt, ...) {
+void luaL_verror (lua_State *L, const char *fmt, ...) {
   char buff[500];
   va_list argp;
   va_start(argp, fmt);
   vsprintf(buff, fmt, argp);
   va_end(argp);
-  lua_error(buff);
+  lua_error(L, buff);
 }
 
 

+ 63 - 22
lauxlib.h

@@ -1,5 +1,5 @@
 /*
-** $Id: lauxlib.h,v 1.12 1999/03/10 14:19:41 roberto Exp roberto $
+** $Id: lauxlib.h,v 1.13 1999/08/16 20:52:00 roberto Exp roberto $
 ** Auxiliary functions for building Lua libraries
 ** See Copyright Notice in lua.h
 */
@@ -18,36 +18,77 @@ struct luaL_reg {
 };
 
 
+#ifdef LUA_REENTRANT
+
+#define luaL_arg_check(L, cond,numarg,extramsg) if (!(cond)) \
+                                               luaL_argerror(L, numarg,extramsg)
+#define luaL_check_string(L, n)	(luaL_check_lstr(L, (n), NULL))
+#define luaL_opt_string(L, n, d)	(luaL_opt_lstr(L, (n), (d), NULL))
+#define luaL_check_int(L, n)	((int)luaL_check_number(L, n))
+#define luaL_check_long(L, n)	((long)luaL_check_number(L, n))
+#define luaL_opt_int(L, n,d)	((int)luaL_opt_number(L, n,d))
+#define luaL_opt_long(L, n,d)	((long)luaL_opt_number(L, n,d))
+
+#else
+
 #define luaL_arg_check(cond,numarg,extramsg) if (!(cond)) \
                                                luaL_argerror(numarg,extramsg)
-
-void luaL_openlib (const struct luaL_reg *l, int n);
-void luaL_argerror (int numarg, const char *extramsg);
-#define luaL_check_string(n)  (luaL_check_lstr((n), NULL))
-const char *luaL_check_lstr (int numArg, long *len);
-#define luaL_opt_string(n, d) (luaL_opt_lstr((n), (d), NULL))
-const char *luaL_opt_lstr (int numArg, const char *def, long *len);
-double luaL_check_number (int numArg);
+#define luaL_check_string(n)	(luaL_check_lstr((n), NULL))
+#define luaL_opt_string(n, d)	(luaL_opt_lstr((n), (d), NULL))
 #define luaL_check_int(n)	((int)luaL_check_number(n))
 #define luaL_check_long(n)	((long)luaL_check_number(n))
-double luaL_opt_number (int numArg, double def);
 #define luaL_opt_int(n,d)	((int)luaL_opt_number(n,d))
 #define luaL_opt_long(n,d)	((long)luaL_opt_number(n,d))
-lua_Object luaL_functionarg (int arg);
-lua_Object luaL_tablearg (int arg);
-lua_Object luaL_nonnullarg (int numArg);
-void luaL_verror (const char *fmt, ...);
-char *luaL_openspace (int size);
-void luaL_resetbuffer (void);
-void luaL_addchar (int c);
-int luaL_getsize (void);
-void luaL_addsize (int n);
-int luaL_newbuffer (int size);
-void luaL_oldbuffer (int old);
-char *luaL_buffer (void);
+
+#endif
+
+
+void luaL_openlib (lua_State *L, const struct luaL_reg *l, int n);
+void luaL_argerror (lua_State *L, int numarg, const char *extramsg);
+const char *luaL_check_lstr (lua_State *L, int numArg, long *len);
+const char *luaL_opt_lstr (lua_State *L, int numArg, const char *def, long *len);
+double luaL_check_number (lua_State *L, int numArg);
+double luaL_opt_number (lua_State *L, int numArg, double def);
+lua_Object luaL_functionarg (lua_State *L, int arg);
+lua_Object luaL_tablearg (lua_State *L, int arg);
+lua_Object luaL_nonnullarg (lua_State *L, int numArg);
+void luaL_verror (lua_State *L, const char *fmt, ...);
+char *luaL_openspace (lua_State *L, int size);
+void luaL_resetbuffer (lua_State *L);
+void luaL_addchar (lua_State *L, int c);
+int luaL_getsize (lua_State *L);
+void luaL_addsize (lua_State *L, int n);
+int luaL_newbuffer (lua_State *L, int size);
+void luaL_oldbuffer (lua_State *L, int old);
+char *luaL_buffer (lua_State *L);
 int luaL_findstring (const char *name, const char *const list[]);
 void luaL_chunkid (char *out, const char *source, int len);
 void luaL_filesource (char *out, const char *filename, int len);
 
 
+#ifndef LUA_REENTRANT
+
+#define luaL_openlib(l,n)	(luaL_openlib)(lua_state,l,n)
+#define luaL_argerror(numarg,extramsg)	\
+				(luaL_argerror)(lua_state,numarg,extramsg)
+#define luaL_check_lstr(numArg,len)	(luaL_check_lstr)(lua_state,numArg,len)
+#define luaL_opt_lstr(numArg,def,len)	\
+				(luaL_opt_lstr)(lua_state,numArg,def,len)
+#define luaL_check_number(numArg)	(luaL_check_number)(lua_state,numArg)
+#define luaL_opt_number(numArg,def)	(luaL_opt_number)(lua_state,numArg,def)
+#define luaL_functionarg(arg)	(luaL_functionarg)(lua_state,arg)
+#define luaL_tablearg(arg)	(luaL_tablearg)(lua_state,arg)
+#define luaL_nonnullarg(numArg)	(luaL_nonnullarg)(lua_state,numArg)
+#define luaL_openspace(size)	(luaL_openspace)(lua_state,size)
+#define luaL_resetbuffer()	(luaL_resetbuffer)(lua_state)
+#define luaL_addchar(c)		(luaL_addchar)(lua_state,c)
+#define luaL_getsize()		(luaL_getsize)(lua_state)
+#define luaL_addsize(n)		(luaL_addsize)(lua_state,n)
+#define luaL_newbuffer(size)	(luaL_newbuffer)(lua_state,size)
+#define luaL_oldbuffer(old)	(luaL_oldbuffer)(lua_state,old)
+#define luaL_buffer()		(luaL_buffer)(lua_state)
+
 #endif
+
+#endif
+

+ 18 - 17
lbuffer.c

@@ -1,5 +1,5 @@
 /*
-** $Id: lbuffer.c,v 1.9 1999/02/26 15:48:55 roberto Exp roberto $
+** $Id: lbuffer.c,v 1.10 1999/11/10 15:40:46 roberto Exp roberto $
 ** Auxiliary functions for building Lua libraries
 ** See Copyright Notice in lua.h
 */
@@ -7,6 +7,8 @@
 
 #include <stdio.h>
 
+#define LUA_REENTRANT
+
 #include "lauxlib.h"
 #include "lmem.h"
 #include "lstate.h"
@@ -20,55 +22,54 @@
 #define EXTRABUFF	32
 
 
-#define openspace(size)  if (L->Mbuffnext+(size) > L->Mbuffsize) Openspace(size)
+#define openspace(L, size)  if (L->Mbuffnext+(size) > L->Mbuffsize) Openspace(L, size)
 
-static void Openspace (int size) {
-  lua_State *l = L;  /* to optimize */
-  l->Mbuffsize = (l->Mbuffnext+size+EXTRABUFF)*2;
-  luaM_reallocvector(l->Mbuffer, l->Mbuffsize, char);
+static void Openspace (lua_State *L, int size) {
+  L->Mbuffsize = (L->Mbuffnext+size+EXTRABUFF)*2;
+  luaM_reallocvector(L, L->Mbuffer, L->Mbuffsize, char);
 }
 
 
-char *luaL_openspace (int size) {
-  openspace(size);
+char *luaL_openspace (lua_State *L, int size) {
+  openspace(L, size);
   return L->Mbuffer+L->Mbuffnext;
 }
 
 
-void luaL_addchar (int c) {
-  openspace(1);
+void luaL_addchar (lua_State *L, int c) {
+  openspace(L, 1);
   L->Mbuffer[L->Mbuffnext++] = (char)c;
 }
 
 
-void luaL_resetbuffer (void) {
+void luaL_resetbuffer (lua_State *L) {
   L->Mbuffnext = L->Mbuffbase;
 }
 
 
-void luaL_addsize (int n) {
+void luaL_addsize (lua_State *L, int n) {
   L->Mbuffnext += n;
 }
 
-int luaL_getsize (void) {
+int luaL_getsize (lua_State *L) {
   return L->Mbuffnext-L->Mbuffbase;
 }
 
-int luaL_newbuffer (int size) {
+int luaL_newbuffer (lua_State *L, int size) {
   int old = L->Mbuffbase;
-  openspace(size);
+  openspace(L, size);
   L->Mbuffbase = L->Mbuffnext;
   return old;
 }
 
 
-void luaL_oldbuffer (int old) {
+void luaL_oldbuffer (lua_State *L, int old) {
   L->Mbuffnext = L->Mbuffbase;
   L->Mbuffbase = old;
 }
 
 
-char *luaL_buffer (void) {
+char *luaL_buffer (lua_State *L) {
   return L->Mbuffer+L->Mbuffbase;
 }
 

+ 295 - 296
lbuiltin.c

@@ -1,5 +1,5 @@
 /*
-** $Id: lbuiltin.c,v 1.72 1999/11/11 17:02:40 roberto Exp roberto $
+** $Id: lbuiltin.c,v 1.73 1999/11/16 12:50:48 roberto Exp roberto $
 ** Built-in functions
 ** See Copyright Notice in lua.h
 */
@@ -10,6 +10,8 @@
 #include <stdlib.h>
 #include <string.h>
 
+#define LUA_REENTRANT
+
 #include "lapi.h"
 #include "lauxlib.h"
 #include "lbuiltin.h"
@@ -34,7 +36,7 @@
 */
 
 
-static void pushtagstring (TaggedString *s) {
+static void pushtagstring (lua_State *L, TaggedString *s) {
   ttype(L->stack.top) = LUA_T_STRING;
   tsvalue(L->stack.top) = s;
   incr_top;
@@ -46,29 +48,29 @@ static real getsize (const Hash *h) {
   int i = h->size;
   Node *n = h->node;
   while (i--) {
-    if (ttype(key(n)) == LUA_T_NUMBER && 
-        ttype(val(n)) != LUA_T_NIL &&
-        nvalue(key(n)) > max)
-      max = nvalue(key(n));
+    if (ttype(key(L, n)) == LUA_T_NUMBER && 
+        ttype(val(L, n)) != LUA_T_NIL &&
+        nvalue(key(L, n)) > max)
+      max = nvalue(key(L, n));
     n++;
   }
   return max;
 }
 
 
-static real getnarg (const Hash *a) {
+static real getnarg (lua_State *L, const Hash *a) {
   TObject index;
   const TObject *value;
   /* value = table.n */
   ttype(&index) = LUA_T_STRING;
-  tsvalue(&index) = luaS_new("n");
-  value = luaH_get(a, &index);
+  tsvalue(&index) = luaS_new(L, "n");
+  value = luaH_get(L, a, &index);
   return (ttype(value) == LUA_T_NUMBER) ? nvalue(value) : getsize(a);
 }
 
 
-static Hash *gettable (int arg) {
-  return avalue(luaA_Address(luaL_tablearg(arg)));
+static Hash *gettable (lua_State *L, int arg) {
+  return avalue(luaA_Address(L, luaL_tablearg(L, arg)));
 }
 
 /* }====================================================== */
@@ -85,8 +87,8 @@ static Hash *gettable (int arg) {
 ** If your system does not support "stderr", redefine this function, or
 ** redefine _ERRORMESSAGE so that it won't need _ALERT.
 */
-static void luaB_alert (void) {
-  fputs(luaL_check_string(1), stderr);
+static void luaB_alert (lua_State *L) {
+  fputs(luaL_check_string(L, 1), stderr);
 }
 
 
@@ -94,13 +96,13 @@ static void luaB_alert (void) {
 ** Standard implementation of _ERRORMESSAGE.
 ** The library "iolib" redefines _ERRORMESSAGE for better error information.
 */
-static void error_message (void) {
-  lua_Object al = lua_rawgetglobal("_ALERT");
-  if (lua_isfunction(al)) {  /* avoid error loop if _ALERT is not defined */
+static void error_message (lua_State *L) {
+  lua_Object al = lua_rawgetglobal(L, "_ALERT");
+  if (lua_isfunction(L, al)) {  /* avoid error loop if _ALERT is not defined */
     char buff[600];
-    sprintf(buff, "lua error: %.500s\n", luaL_check_string(1));
-    lua_pushstring(buff);
-    lua_callfunction(al);
+    sprintf(buff, "lua error: %.500s\n", luaL_check_string(L, 1));
+    lua_pushstring(L, buff);
+    lua_callfunction(L, al);
   }
 }
 
@@ -115,142 +117,142 @@ static void error_message (void) {
 #define MAXPRINT	40  /* arbitrary limit */
 #endif
 
-static void luaB_print (void) {
+static void luaB_print (lua_State *L) {
   lua_Object args[MAXPRINT];
   lua_Object obj;
   int n = 0;
   int i;
-  while ((obj = lua_getparam(n+1)) != LUA_NOOBJECT) {
-    luaL_arg_check(n < MAXPRINT, n+1, "too many arguments");
+  while ((obj = lua_getparam(L, n+1)) != LUA_NOOBJECT) {
+    luaL_arg_check(L, n < MAXPRINT, n+1, "too many arguments");
     args[n++] = obj;
   }
   for (i=0; i<n; i++) {
-    lua_pushobject(args[i]);
-    if (lua_call("tostring"))
-      lua_error("error in `tostring' called by `print'");
-    obj = lua_getresult(1);
-    if (!lua_isstring(obj))
-      lua_error("`tostring' must return a string to `print'");
+    lua_pushobject(L, args[i]);
+    if (lua_call(L, "tostring"))
+      lua_error(L, "error in `tostring' called by `print'");
+    obj = lua_getresult(L, 1);
+    if (!lua_isstring(L, obj))
+      lua_error(L, "`tostring' must return a string to `print'");
     if (i>0) fputs("\t", stdout);
-    fputs(lua_getstring(obj), stdout);
+    fputs(lua_getstring(L, obj), stdout);
   }
   fputs("\n", stdout);
 }
 
 
-static void luaB_tonumber (void) {
-  int base = luaL_opt_int(2, 10);
+static void luaB_tonumber (lua_State *L) {
+  int base = luaL_opt_int(L, 2, 10);
   if (base == 10) {  /* standard conversion */
-    lua_Object o = lua_getparam(1);
-    if (lua_isnumber(o)) lua_pushnumber(lua_getnumber(o));
-    else lua_pushnil();  /* not a number */
+    lua_Object o = lua_getparam(L, 1);
+    if (lua_isnumber(L, o)) lua_pushnumber(L, lua_getnumber(L, o));
+    else lua_pushnil(L);  /* not a number */
   }
   else {
-    const char *s1 = luaL_check_string(1);
+    const char *s1 = luaL_check_string(L, 1);
     char *s2;
     real n;
-    luaL_arg_check(0 <= base && base <= 36, 2, "base out of range");
+    luaL_arg_check(L, 0 <= base && base <= 36, 2, "base out of range");
     n = strtoul(s1, &s2, base);
     if (s1 == s2) return;  /* no valid digits: return nil */
     while (isspace((unsigned char)*s2)) s2++;  /* skip trailing spaces */
     if (*s2) return;  /* invalid trailing character: return nil */
-    lua_pushnumber(n);
+    lua_pushnumber(L, n);
   }
 }
 
 
-static void luaB_error (void) {
-  lua_error(lua_getstring(lua_getparam(1)));
+static void luaB_error (lua_State *L) {
+  lua_error(L, lua_getstring(L, lua_getparam(L, 1)));
 }
 
-static void luaB_setglobal (void) {
-  const char *n = luaL_check_string(1);
-  lua_Object value = luaL_nonnullarg(2);
-  lua_pushobject(value);
-  lua_setglobal(n);
-  lua_pushobject(value);  /* return given value */
+static void luaB_setglobal (lua_State *L) {
+  const char *n = luaL_check_string(L, 1);
+  lua_Object value = luaL_nonnullarg(L, 2);
+  lua_pushobject(L, value);
+  lua_setglobal(L, n);
+  lua_pushobject(L, value);  /* return given value */
 }
 
-static void luaB_rawsetglobal (void) {
-  const char *n = luaL_check_string(1);
-  lua_Object value = luaL_nonnullarg(2);
-  lua_pushobject(value);
-  lua_rawsetglobal(n);
-  lua_pushobject(value);  /* return given value */
+static void luaB_rawsetglobal (lua_State *L) {
+  const char *n = luaL_check_string(L, 1);
+  lua_Object value = luaL_nonnullarg(L, 2);
+  lua_pushobject(L, value);
+  lua_rawsetglobal(L, n);
+  lua_pushobject(L, value);  /* return given value */
 }
 
-static void luaB_getglobal (void) {
-  lua_pushobject(lua_getglobal(luaL_check_string(1)));
+static void luaB_getglobal (lua_State *L) {
+  lua_pushobject(L, lua_getglobal(L, luaL_check_string(L, 1)));
 }
 
-static void luaB_rawgetglobal (void) {
-  lua_pushobject(lua_rawgetglobal(luaL_check_string(1)));
+static void luaB_rawgetglobal (lua_State *L) {
+  lua_pushobject(L, lua_rawgetglobal(L, luaL_check_string(L, 1)));
 }
 
-static void luaB_luatag (void) {
-  lua_pushnumber(lua_tag(lua_getparam(1)));
+static void luaB_luatag (lua_State *L) {
+  lua_pushnumber(L, lua_tag(L, lua_getparam(L, 1)));
 }
 
-static void luaB_settag (void) {
-  lua_Object o = luaL_tablearg(1);
-  lua_pushobject(o);
-  lua_settag(luaL_check_int(2));
-  lua_pushobject(o);  /* return first argument */
+static void luaB_settag (lua_State *L) {
+  lua_Object o = luaL_tablearg(L, 1);
+  lua_pushobject(L, o);
+  lua_settag(L, luaL_check_int(L, 2));
+  lua_pushobject(L, o);  /* return first argument */
 }
 
-static void luaB_newtag (void) {
-  lua_pushnumber(lua_newtag());
+static void luaB_newtag (lua_State *L) {
+  lua_pushnumber(L, lua_newtag(L));
 }
 
-static void luaB_copytagmethods (void) {
-  lua_pushnumber(lua_copytagmethods(luaL_check_int(1),
-                                    luaL_check_int(2)));
+static void luaB_copytagmethods (lua_State *L) {
+  lua_pushnumber(L, lua_copytagmethods(L, luaL_check_int(L, 1),
+                                    luaL_check_int(L, 2)));
 }
 
-static void luaB_rawgettable (void) {
-  lua_pushobject(luaL_nonnullarg(1));
-  lua_pushobject(luaL_nonnullarg(2));
-  lua_pushobject(lua_rawgettable());
+static void luaB_rawgettable (lua_State *L) {
+  lua_pushobject(L, luaL_nonnullarg(L, 1));
+  lua_pushobject(L, luaL_nonnullarg(L, 2));
+  lua_pushobject(L, lua_rawgettable(L));
 }
 
-static void luaB_rawsettable (void) {
-  lua_pushobject(luaL_nonnullarg(1));
-  lua_pushobject(luaL_nonnullarg(2));
-  lua_pushobject(luaL_nonnullarg(3));
-  lua_rawsettable();
+static void luaB_rawsettable (lua_State *L) {
+  lua_pushobject(L, luaL_nonnullarg(L, 1));
+  lua_pushobject(L, luaL_nonnullarg(L, 2));
+  lua_pushobject(L, luaL_nonnullarg(L, 3));
+  lua_rawsettable(L);
 }
 
-static void luaB_settagmethod (void) {
-  int tag = luaL_check_int(1);
-  const char *event = luaL_check_string(2);
-  lua_Object nf = luaL_nonnullarg(3);
+static void luaB_settagmethod (lua_State *L) {
+  int tag = luaL_check_int(L, 1);
+  const char *event = luaL_check_string(L, 2);
+  lua_Object nf = luaL_nonnullarg(L, 3);
 #ifndef LUA_COMPAT_GC
   if (strcmp(event, "gc") == 0 && tag != LUA_T_NIL)
-    lua_error("cannot set this tag method from Lua");
+    lua_error(L, "cannot set this tag method from Lua");
 #endif
-  lua_pushobject(nf);
-  lua_pushobject(lua_settagmethod(tag, event));
+  lua_pushobject(L, nf);
+  lua_pushobject(L, lua_settagmethod(L, tag, event));
 }
 
-static void luaB_gettagmethod (void) {
-  lua_pushobject(lua_gettagmethod(luaL_check_int(1), luaL_check_string(2)));
+static void luaB_gettagmethod (lua_State *L) {
+  lua_pushobject(L, lua_gettagmethod(L, luaL_check_int(L, 1), luaL_check_string(L, 2)));
 }
 
-static void luaB_seterrormethod (void) {
-  lua_Object nf = luaL_functionarg(1);
-  lua_pushobject(nf);
-  lua_pushobject(lua_seterrormethod());
+static void luaB_seterrormethod (lua_State *L) {
+  lua_Object nf = luaL_functionarg(L, 1);
+  lua_pushobject(L, nf);
+  lua_pushobject(L, lua_seterrormethod(L));
 }
 
-static void luaB_collectgarbage (void) {
-  lua_pushnumber(lua_collectgarbage(luaL_opt_int(1, 0)));
+static void luaB_collectgarbage (lua_State *L) {
+  lua_pushnumber(L, lua_collectgarbage(L, luaL_opt_int(L, 1, 0)));
 }
 
 
-static void luaB_type (void) {
-  lua_Object o = luaL_nonnullarg(1);
-  lua_pushstring(lua_type(o));
-  lua_pushnumber(lua_tag(o));
+static void luaB_type (lua_State *L) {
+  lua_Object o = luaL_nonnullarg(L, 1);
+  lua_pushstring(L, lua_type(L, o));
+  lua_pushnumber(L, lua_tag(L, o));
 }
 
 /* }====================================================== */
@@ -264,62 +266,62 @@ static void luaB_type (void) {
 */
 
 
-static void passresults (void) {
+static void passresults (lua_State *L) {
   L->Cstack.base = L->Cstack.lua2C;  /* position of first result */
   if (L->Cstack.num == 0)
-    lua_pushuserdata(NULL);  /* at least one result to signal no errors */
+    lua_pushuserdata(L, NULL);  /* at least one result to signal no errors */
 }
 
-static void luaB_dostring (void) {
+static void luaB_dostring (lua_State *L) {
   long l;
-  const char *s = luaL_check_lstr(1, &l);
+  const char *s = luaL_check_lstr(L, 1, &l);
   if (*s == ID_CHUNK)
-    lua_error("`dostring' cannot run pre-compiled code");
-  if (lua_dobuffer(s, l, luaL_opt_string(2, s)) == 0)
-    passresults();
+    lua_error(L, "`dostring' cannot run pre-compiled code");
+  if (lua_dobuffer(L, s, l, luaL_opt_string(L, 2, s)) == 0)
+    passresults(L);
   /* else return no value */
 }
 
 
-static void luaB_dofile (void) {
-  const char *fname = luaL_opt_string(1, NULL);
-  if (lua_dofile(fname) == 0)
-    passresults();
+static void luaB_dofile (lua_State *L) {
+  const char *fname = luaL_opt_string(L, 1, NULL);
+  if (lua_dofile(L, fname) == 0)
+    passresults(L);
   /* else return no value */
 }
 
 
-static void luaB_call (void) {
-  lua_Object f = luaL_nonnullarg(1);
-  const Hash *arg = gettable(2);
-  const char *options = luaL_opt_string(3, "");
-  lua_Object err = lua_getparam(4);
-  int narg = (int)getnarg(arg);
+static void luaB_call (lua_State *L) {
+  lua_Object f = luaL_nonnullarg(L, 1);
+  const Hash *arg = gettable(L, 2);
+  const char *options = luaL_opt_string(L, 3, "");
+  lua_Object err = lua_getparam(L, 4);
+  int narg = (int)getnarg(L, arg);
   int i, status;
   if (err != LUA_NOOBJECT) {  /* set new error method */
-    lua_pushobject(err);
-    err = lua_seterrormethod();
+    lua_pushobject(L, err);
+    err = lua_seterrormethod(L);
   }
   /* push arg[1...n] */
-  luaD_checkstack(narg);
+  luaD_checkstack(L, narg);
   for (i=0; i<narg; i++)
-    *(L->stack.top++) = *luaH_getint(arg, i+1);
-  status = lua_callfunction(f);
+    *(L->stack.top++) = *luaH_getint(L, arg, i+1);
+  status = lua_callfunction(L, f);
   if (err != LUA_NOOBJECT) {  /* restore old error method */
-    lua_pushobject(err);
-    lua_seterrormethod();
+    lua_pushobject(L, err);
+    lua_seterrormethod(L);
   }
   if (status != 0) {  /* error in call? */
     if (strchr(options, 'x')) {
-      lua_pushnil();
+      lua_pushnil(L);
       return;  /* return nil to signal the error */
     }
     else
-      lua_error(NULL);
+      lua_error(L, NULL);
   }
   else {  /* no errors */
     if (strchr(options, 'p')) {  /* pack results? */
-      luaV_pack(L->Cstack.lua2C, L->Cstack.num, L->stack.top);
+      luaV_pack(L, L->Cstack.lua2C, L->Cstack.num, L->stack.top);
       incr_top;
     }
     else
@@ -328,45 +330,45 @@ static void luaB_call (void) {
 }
 
 
-static void luaB_nextvar (void) {
-  const TObject *o = luaA_Address(luaL_nonnullarg(1));
+static void luaB_nextvar (lua_State *L) {
+  const TObject *o = luaA_Address(L, luaL_nonnullarg(L, 1));
   TaggedString *g;
   if (ttype(o) == LUA_T_NIL)
     g = NULL;
   else {
-    luaL_arg_check(ttype(o) == LUA_T_STRING, 1, "variable name expected");
+    luaL_arg_check(L, ttype(o) == LUA_T_STRING, 1, "variable name expected");
     g = tsvalue(o);
   }
-  if (!luaA_nextvar(g))
-    lua_pushnil();
+  if (!luaA_nextvar(L, g))
+    lua_pushnil(L);
 }
 
 
-static void luaB_next (void) {
-  const Hash *a = gettable(1);
-  const TObject *k = luaA_Address(luaL_nonnullarg(2));
+static void luaB_next (lua_State *L) {
+  const Hash *a = gettable(L, 1);
+  const TObject *k = luaA_Address(L, luaL_nonnullarg(L, 2));
   int i;  /* will get first element after `i' */
   if (ttype(k) == LUA_T_NIL)
     i = 0;  /* get first */
   else {
-    i = luaH_pos(a, k)+1;
-    luaL_arg_check(i != 0, 2, "key not found");
+    i = luaH_pos(L, a, k)+1;
+    luaL_arg_check(L, i != 0, 2, "key not found");
   }
-  if (luaA_next(a, i) == 0)
-    lua_pushnil();
+  if (luaA_next(L, a, i) == 0)
+    lua_pushnil(L);
 }
 
 
-static void luaB_tostring (void) {
-  lua_Object obj = lua_getparam(1);
-  const TObject *o = luaA_Address(obj);
+static void luaB_tostring (lua_State *L) {
+  lua_Object obj = lua_getparam(L, 1);
+  const TObject *o = luaA_Address(L, obj);
   char buff[64];
   switch (ttype(o)) {
     case LUA_T_NUMBER:
-      lua_pushstring(lua_getstring(obj));
+      lua_pushstring(L, lua_getstring(L, obj));
       return;
     case LUA_T_STRING:
-      lua_pushobject(obj);
+      lua_pushobject(L, obj);
       return;
     case LUA_T_ARRAY:
       sprintf(buff, "table: %p", o->value.a);
@@ -384,12 +386,12 @@ static void luaB_tostring (void) {
       sprintf(buff, "userdata: %p", o->value.ts->u.d.value);
       break;
     case LUA_T_NIL:
-      lua_pushstring("nil");
+      lua_pushstring(L, "nil");
       return;
     default:
-      LUA_INTERNALERROR("invalid type");
+      LUA_INTERNALERROR(L, "invalid type");
   }
-  lua_pushstring(buff);
+  lua_pushstring(L, buff);
 }
 
 /* }====================================================== */
@@ -406,28 +408,28 @@ static void luaB_tostring (void) {
 ** =======================================================
 */
 
-static void luaB_assert (void) {
-  lua_Object p = lua_getparam(1);
-  if (p == LUA_NOOBJECT || lua_isnil(p))
-    luaL_verror("assertion failed!  %.90s", luaL_opt_string(2, ""));
+static void luaB_assert (lua_State *L) {
+  lua_Object p = lua_getparam(L, 1);
+  if (p == LUA_NOOBJECT || lua_isnil(L, p))
+    luaL_verror(L, "assertion failed!  %.90s", luaL_opt_string(L, 2, ""));
 }
 
 
-static void luaB_foreachi (void) {
-  const Hash *t = gettable(1);
+static void luaB_foreachi (lua_State *L) {
+  const Hash *t = gettable(L, 1);
   int i;
-  int n = (int)getnarg(t);
+  int n = (int)getnarg(L, t);
   TObject f;
   /* 'f' cannot be a pointer to TObject, because it is on the stack, and the
      stack may be reallocated by the call. Moreover, some C compilers do not
      initialize structs, so we must do the assignment after the declaration */
-  f = *luaA_Address(luaL_functionarg(2));
-  luaD_checkstack(3);  /* for f, key, and val */
+  f = *luaA_Address(L, luaL_functionarg(L, 2));
+  luaD_checkstack(L, 3);  /* for f, key, and val */
   for (i=1; i<=n; i++) {
     *(L->stack.top++) = f;
     ttype(L->stack.top) = LUA_T_NUMBER; nvalue(L->stack.top++) = i;
-    *(L->stack.top++) = *luaH_getint(t, i);
-    luaD_calln(2, 1);
+    *(L->stack.top++) = *luaH_getint(L, t, i);
+    luaD_calln(L, 2, 1);
     if (ttype(L->stack.top-1) != LUA_T_NIL)
       return;
     L->stack.top--;
@@ -435,19 +437,19 @@ static void luaB_foreachi (void) {
 }
 
 
-static void luaB_foreach (void) {
-  const Hash *a = gettable(1);
+static void luaB_foreach (lua_State *L) {
+  const Hash *a = gettable(L, 1);
   int i;
   TObject f;  /* see comment in 'foreachi' */
-  f = *luaA_Address(luaL_functionarg(2));
-  luaD_checkstack(3);  /* for f, key, and val */
+  f = *luaA_Address(L, luaL_functionarg(L, 2));
+  luaD_checkstack(L, 3);  /* for f, key, and val */
   for (i=0; i<a->size; i++) {
     const Node *nd = &(a->node[i]);
-    if (ttype(val(nd)) != LUA_T_NIL) {
+    if (ttype(val(L, nd)) != LUA_T_NIL) {
       *(L->stack.top++) = f;
-      *(L->stack.top++) = *key(nd);
-      *(L->stack.top++) = *val(nd);
-      luaD_calln(2, 1);
+      *(L->stack.top++) = *key(L, nd);
+      *(L->stack.top++) = *val(L, nd);
+      luaD_calln(L, 2, 1);
       if (ttype(L->stack.top-1) != LUA_T_NIL)
         return;
       L->stack.top--;  /* remove result */
@@ -456,18 +458,18 @@ static void luaB_foreach (void) {
 }
 
 
-static void luaB_foreachvar (void) {
+static void luaB_foreachvar (lua_State *L) {
   GlobalVar *gv;
   TObject f;  /* see comment in 'foreachi' */
-  f = *luaA_Address(luaL_functionarg(1));
-  luaD_checkstack(4);  /* for extra var name, f, var name, and globalval */
+  f = *luaA_Address(L, luaL_functionarg(L, 1));
+  luaD_checkstack(L, 4);  /* for extra var name, f, var name, and globalval */
   for (gv = L->rootglobal; gv; gv = gv->next) {
     if (gv->value.ttype != LUA_T_NIL) {
-      pushtagstring(gv->name);  /* keep (extra) name on stack to avoid GC */
+      pushtagstring(L, gv->name);  /* keep (extra) name on stack to avoid GC */
       *(L->stack.top++) = f;
-      pushtagstring(gv->name);
+      pushtagstring(L, gv->name);
       *(L->stack.top++) = gv->value;
-      luaD_calln(2, 1);
+      luaD_calln(L, 2, 1);
       if (ttype(L->stack.top-1) != LUA_T_NIL) {
         L->stack.top--;
         *(L->stack.top-1) = *L->stack.top;  /* remove extra name */
@@ -479,39 +481,39 @@ static void luaB_foreachvar (void) {
 }
 
 
-static void luaB_getn (void) {
-  lua_pushnumber(getnarg(gettable(1)));
+static void luaB_getn (lua_State *L) {
+  lua_pushnumber(L, getnarg(L, gettable(L, 1)));
 }
 
 
-static void luaB_tinsert (void) {
-  Hash *a = gettable(1);
-  lua_Object v = lua_getparam(3);
-  int n = (int)getnarg(a);
+static void luaB_tinsert (lua_State *L) {
+  Hash *a = gettable(L, 1);
+  lua_Object v = lua_getparam(L, 3);
+  int n = (int)getnarg(L, a);
   int pos;
   if (v != LUA_NOOBJECT)
-    pos = luaL_check_int(2);
+    pos = luaL_check_int(L, 2);
   else {  /* called with only 2 arguments */
-    v = luaL_nonnullarg(2);
+    v = luaL_nonnullarg(L, 2);
     pos = n+1;
   }
-  luaV_setn(a, n+1);  /* a.n = n+1 */
+  luaV_setn(L, a, n+1);  /* a.n = n+1 */
   for ( ;n>=pos; n--)
-    luaH_move(a, n, n+1);  /* a[n+1] = a[n] */
-  luaH_setint(a, pos, luaA_Address(v));  /* a[pos] = v */
+    luaH_move(L, a, n, n+1);  /* a[n+1] = a[n] */
+  luaH_setint(L, a, pos, luaA_Address(L, v));  /* a[pos] = v */
 }
 
 
-static void luaB_tremove (void) {
-  Hash *a = gettable(1);
-  int n = (int)getnarg(a);
-  int pos = luaL_opt_int(2, n);
+static void luaB_tremove (lua_State *L) {
+  Hash *a = gettable(L, 1);
+  int n = (int)getnarg(L, a);
+  int pos = luaL_opt_int(L, 2, n);
   if (n <= 0) return;  /* table is "empty" */
-  luaA_pushobject(luaH_getint(a, pos));  /* result = a[pos] */
+  luaA_pushobject(L, luaH_getint(L, a, pos));  /* result = a[pos] */
   for ( ;pos<n; pos++)
-    luaH_move(a, pos+1, pos);  /* a[pos] = a[pos+1] */
-  luaV_setn(a, n-1);  /* a.n = n-1 */
-  luaH_setint(a, n, &luaO_nilobject);  /* a[n] = nil */
+    luaH_move(L, a, pos+1, pos);  /* a[pos] = a[pos+1] */
+  luaV_setn(L, a, n-1);  /* a.n = n-1 */
+  luaH_setint(L, a, n, &luaO_nilobject);  /* a[n] = nil */
 }
 
 
@@ -520,63 +522,63 @@ static void luaB_tremove (void) {
 ** Quicksort
 */
 
-static void swap (Hash *a, int i, int j) {
+static void swap (lua_State *L, Hash *a, int i, int j) {
   TObject temp;
-  temp = *luaH_getint(a, i);
-  luaH_move(a, j, i);
-  luaH_setint(a, j, &temp);
+  temp = *luaH_getint(L, a, i);
+  luaH_move(L, a, j, i);
+  luaH_setint(L, a, j, &temp);
 }
 
-static int sort_comp (lua_Object f, const TObject *a, const TObject *b) {
+static int sort_comp (lua_State *L, lua_Object f, const TObject *a, const TObject *b) {
   /* notice: the caller (auxsort) must check stack space */
   if (f != LUA_NOOBJECT) {
-    *(L->stack.top) = *luaA_Address(f);
+    *(L->stack.top) = *luaA_Address(L, f);
     *(L->stack.top+1) = *a;
     *(L->stack.top+2) = *b;
     L->stack.top += 3;
-    luaD_calln(2, 1);
+    luaD_calln(L, 2, 1);
   }
   else {  /* a < b? */
     *(L->stack.top) = *a;
     *(L->stack.top+1) = *b;
     L->stack.top += 2;
-    luaV_comparison(LUA_T_NUMBER, LUA_T_NIL, LUA_T_NIL, IM_LT);
+    luaV_comparison(L, LUA_T_NUMBER, LUA_T_NIL, LUA_T_NIL, IM_LT);
   }
   return ttype(--(L->stack.top)) != LUA_T_NIL;
 }
 
-static void auxsort (Hash *a, int l, int u, lua_Object f) {
+static void auxsort (lua_State *L, Hash *a, int l, int u, lua_Object f) {
   StkId P = L->stack.top - L->stack.stack;  /* temporary place for pivot */
   L->stack.top++;
   ttype(L->stack.stack+P) = LUA_T_NIL;
   while (l < u) {  /* for tail recursion */
     int i, j;
     /* sort elements a[l], a[(l+u)/2] and a[u] */
-    if (sort_comp(f, luaH_getint(a, u), luaH_getint(a, l)))  /* a[u]<a[l]? */
-      swap(a, l, u);
+    if (sort_comp(L, f, luaH_getint(L, a, u), luaH_getint(L, a, l)))  /* a[u]<a[l]? */
+      swap(L, a, l, u);
     if (u-l == 1) break;  /* only 2 elements */
     i = (l+u)/2;
-    *(L->stack.stack+P) = *luaH_getint(a, i);  /* P = a[i] */
-    if (sort_comp(f, L->stack.stack+P, luaH_getint(a, l)))  /* a[i]<a[l]? */
-      swap(a, l, i);
-    else if (sort_comp(f, luaH_getint(a, u), L->stack.stack+P)) /* a[u]<a[i]? */
-      swap(a, i, u);
+    *(L->stack.stack+P) = *luaH_getint(L, a, i);  /* P = a[i] */
+    if (sort_comp(L, f, L->stack.stack+P, luaH_getint(L, a, l)))  /* a[i]<a[l]? */
+      swap(L, a, l, i);
+    else if (sort_comp(L, f, luaH_getint(L, a, u), L->stack.stack+P)) /* a[u]<a[i]? */
+      swap(L, a, i, u);
     if (u-l == 2) break;  /* only 3 elements */
-    *(L->stack.stack+P) = *luaH_getint(a, i); /* save pivot on stack (for GC) */
-    swap(a, i, u-1);  /* put median element as pivot (a[u-1]) */
+    *(L->stack.stack+P) = *luaH_getint(L, a, i); /* save pivot on stack (GC) */
+    swap(L, a, i, u-1);  /* put median element as pivot (a[u-1]) */
     /* a[l] <= P == a[u-1] <= a[u], only needs to sort from l+1 to u-2 */
     i = l; j = u-1;
-    for  (;;) {  /* invariant: a[l..i] <= P <= a[j..u] */
+    for (;;) {  /* invariant: a[l..i] <= P <= a[j..u] */
       /* repeat i++ until a[i] >= P */
-      while (sort_comp(f, luaH_getint(a, ++i), L->stack.stack+P))
-        if (i>u) lua_error("invalid order function for sorting");
+      while (sort_comp(L, f, luaH_getint(L, a, ++i), L->stack.stack+P))
+        if (i>u) lua_error(L, "invalid order function for sorting");
       /* repeat j-- until a[j] <= P */
-      while (sort_comp(f, (L->stack.stack+P), luaH_getint(a, --j)))
-        if (j<l) lua_error("invalid order function for sorting");
+      while (sort_comp(L, f, (L->stack.stack+P), luaH_getint(L, a, --j)))
+        if (j<l) lua_error(L, "invalid order function for sorting");
       if (j<i) break;
-      swap(a, i, j);
+      swap(L, a, i, j);
     }
-    swap(a, u-1, i);  /* swap pivot (a[u-1]) with a[i] */
+    swap(L, a, u-1, i);  /* swap pivot (a[u-1]) with a[i] */
     /* a[l..i-1] <= a[i] == P <= a[i+1..u] */
     /* adjust so that smaller "half" is in [j..i] and larger one in [l..u] */
     if (i-l < u-i) {
@@ -585,21 +587,21 @@ static void auxsort (Hash *a, int l, int u, lua_Object f) {
     else {
       j=i+1; i=u; u=j-2;
     }
-    auxsort(a, j, i, f);  /* call recursively the smaller one */
+    auxsort(L, a, j, i, f);  /* call recursively the smaller one */
   }  /* repeat the routine for the larger one */
   L->stack.top--;  /* remove pivot from stack */
 }
 
-static void luaB_sort (void) {
-  lua_Object t = lua_getparam(1);
-  Hash *a = gettable(1);
-  int n = (int)getnarg(a);
-  lua_Object func = lua_getparam(2);
-  luaL_arg_check(func == LUA_NOOBJECT || lua_isfunction(func), 2,
+static void luaB_sort (lua_State *L) {
+  lua_Object t = lua_getparam(L, 1);
+  Hash *a = gettable(L, 1);
+  int n = (int)getnarg(L, a);
+  lua_Object func = lua_getparam(L, 2);
+  luaL_arg_check(L, func == LUA_NOOBJECT || lua_isfunction(L, func), 2,
                  "function expected");
-  luaD_checkstack(4);  /* for Pivot, f, a, b (sort_comp) */
-  auxsort(a, 1, n, func);
-  lua_pushobject(t);
+  luaD_checkstack(L, 4);  /* for Pivot, f, a, b (sort_comp) */
+  auxsort(L, a, 1, n, func);
+  lua_pushobject(L, t);
 }
 
 /* }====================================================== */
@@ -617,138 +619,138 @@ static void luaB_sort (void) {
 ** =======================================================
 */
 
-static void mem_query (void) {
-  lua_pushnumber(totalmem);
-  lua_pushnumber(numblocks);
+static void mem_query (lua_State *L) {
+  lua_pushnumber(L, totalmem);
+  lua_pushnumber(L, numblocks);
 }
 
 
-static void hash_query (void) {
-  const TObject *o = luaA_Address(luaL_nonnullarg(1));
-  if (lua_getparam(2) == LUA_NOOBJECT) {
-    luaL_arg_check(ttype(o) == LUA_T_STRING, 1, "string expected");
-    lua_pushnumber(tsvalue(o)->hash);
+static void hash_query (lua_State *L) {
+  const TObject *o = luaA_Address(L, luaL_nonnullarg(L, 1));
+  if (lua_getparam(L, 2) == LUA_NOOBJECT) {
+    luaL_arg_check(L, ttype(o) == LUA_T_STRING, 1, "string expected");
+    lua_pushnumber(L, tsvalue(o)->hash);
   }
   else {
-    const Hash *t = avalue(luaA_Address(luaL_tablearg(2)));
-    lua_pushnumber(luaH_mainposition(t, o) - t->node);
+    const Hash *t = avalue(luaA_Address(L, luaL_tablearg(L, 2)));
+    lua_pushnumber(L, luaH_mainposition(L, t, o) - t->node);
   }
 }
 
 
-static void table_query (void) {
-  const Hash *t = avalue(luaA_Address(luaL_tablearg(1)));
-  int i = luaL_opt_int(2, -1);
+static void table_query (lua_State *L) {
+  const Hash *t = avalue(luaA_Address(L, luaL_tablearg(L, 1)));
+  int i = luaL_opt_int(L, 2, -1);
   if (i == -1) {
-    lua_pushnumber(t->size);
-    lua_pushnumber(t->firstfree - t->node);
+    lua_pushnumber(L, t->size);
+    lua_pushnumber(L, t->firstfree - t->node);
   }
   else if (i < t->size) {
-    luaA_pushobject(&t->node[i].key);
-    luaA_pushobject(&t->node[i].val);
+    luaA_pushobject(L, &t->node[i].key);
+    luaA_pushobject(L, &t->node[i].val);
     if (t->node[i].next)
-      lua_pushnumber(t->node[i].next - t->node);
+      lua_pushnumber(L, t->node[i].next - t->node);
   }
 }
 
 
-static void query_strings (void) {
-  int h = luaL_check_int(1) - 1;
-  int s = luaL_opt_int(2, 0) - 1;
+static void query_strings (lua_State *L) {
+  int h = luaL_check_int(L, 1) - 1;
+  int s = luaL_opt_int(L, 2, 0) - 1;
   if (s==-1) {
     if (h < NUM_HASHS) {
-      lua_pushnumber(L->string_root[h].nuse);
-      lua_pushnumber(L->string_root[h].size);
+      lua_pushnumber(L, L->string_root[h].nuse);
+      lua_pushnumber(L, L->string_root[h].size);
     }
   }
   else {
     TaggedString *ts = L->string_root[h].hash[s];
     for (ts = L->string_root[h].hash[s]; ts; ts = ts->nexthash) {
-      if (ts->constindex == -1) lua_pushstring("<USERDATA>");
-      else lua_pushstring(ts->str);
+      if (ts->constindex == -1) lua_pushstring(L, "<USERDATA>");
+      else lua_pushstring(L, ts->str);
     }
   }
 }
 
 
-static void extra_services (void) {
-  const char *service = luaL_check_string(1);
+static void extra_services (lua_State *L) {
+  const char *service = luaL_check_string(L, 1);
   switch (*service) {
     case 'U':  /* create a userdata with a given value/tag */
-      lua_pushusertag((void *)luaL_check_int(2), luaL_check_int(3));
+      lua_pushusertag(L, (void *)luaL_check_int(L, 2), luaL_check_int(L, 3));
       break;
 
     case 'u':  /* return the value of a userdata */
-      lua_pushnumber((int)lua_getuserdata(lua_getparam(2)));
+      lua_pushnumber(L, (int)lua_getuserdata(L, lua_getparam(L, 2)));
       break;
 
     case 't':  /* set `gc' tag method */
-      lua_pushobject(lua_getparam(3));
-      lua_settagmethod(luaL_check_int(2), "gc");
+      lua_pushobject(L, lua_getparam(L, 3));
+      lua_settagmethod(L, luaL_check_int(L, 2), "gc");
       break;
 
-    default: luaL_argerror(1, "invalid service");
+    default: luaL_argerror(L, 1, "invalid service");
   }
 }
 
 
-static void testC (void) {
-#define getnum(s)	((*s++) - '0')
-#define getname(s)	(nome[0] = *s++, nome)
+static void testC (lua_State *L) {
+#define getnum(L, s)	((*s++) - '0')
+#define getname(L, s)	(nome[0] = *s++, nome)
 
   lua_Object reg[10];
   char nome[2];
-  const char *s = luaL_check_string(1);
+  const char *s = luaL_check_string(L, 1);
   nome[1] = 0;
   for (;;) {
     switch (*s++) {
       case '0': case '1': case '2': case '3': case '4':
       case '5': case '6': case '7': case '8': case '9':
-        lua_pushnumber(*(s-1) - '0');
+        lua_pushnumber(L, *(s-1) - '0');
         break;
 
-      case 'c': reg[getnum(s)] = lua_createtable(); break;
-      case 'C': { lua_CFunction f = lua_getcfunction(lua_getglobal(getname(s)));
-                  lua_pushcclosure(f, getnum(s));
+      case 'c': reg[getnum(L, s)] = lua_createtable(L); break;
+      case 'C': { lua_CFunction f = lua_getcfunction(L, lua_getglobal(L, getname(L, s)));
+                  lua_pushcclosure(L, f, getnum(L, s));
                   break;
                 }
-      case 'P': reg[getnum(s)] = lua_pop(); break;
-      case 'g': { int n=getnum(s); reg[n]=lua_getglobal(getname(s)); break; }
-      case 'G': { int n = getnum(s);
-                  reg[n] = lua_rawgetglobal(getname(s));
+      case 'P': reg[getnum(L, s)] = lua_pop(L); break;
+      case 'g': { int n=getnum(L, s); reg[n]=lua_getglobal(L, getname(L, s)); break; }
+      case 'G': { int n = getnum(L, s);
+                  reg[n] = lua_rawgetglobal(L, getname(L, s));
                   break;
                 }
-      case 'l': lua_pushnumber(lua_ref(1)); reg[getnum(s)] = lua_pop(); break;
-      case 'L': lua_pushnumber(lua_ref(0)); reg[getnum(s)] = lua_pop(); break;
-      case 'r': { int n=getnum(s);
-                  reg[n]=lua_getref((int)lua_getnumber(reg[getnum(s)]));
+      case 'l': lua_pushnumber(L, lua_ref(L, 1)); reg[getnum(L, s)] = lua_pop(L); break;
+      case 'L': lua_pushnumber(L, lua_ref(L, 0)); reg[getnum(L, s)] = lua_pop(L); break;
+      case 'r': { int n=getnum(L, s);
+                  reg[n]=lua_getref(L, (int)lua_getnumber(L, reg[getnum(L, s)]));
                   break;
                 }
-      case 'u': lua_unref((int)lua_getnumber(reg[getnum(s)]));
+      case 'u': lua_unref(L, (int)lua_getnumber(L, reg[getnum(L, s)]));
                 break;
-      case 'p': { int n = getnum(s); reg[n] = lua_getparam(getnum(s)); break; }
-      case '=': lua_setglobal(getname(s)); break;
-      case 's': lua_pushstring(getname(s)); break;
-      case 'o': lua_pushobject(reg[getnum(s)]); break;
-      case 'f': lua_call(getname(s)); break;
-      case 'i': reg[getnum(s)] = lua_gettable(); break;
-      case 'I': reg[getnum(s)] = lua_rawgettable(); break;
-      case 't': lua_settable(); break;
-      case 'T': lua_rawsettable(); break;
-      case 'N' : lua_pushstring(lua_nextvar(lua_getstring(reg[getnum(s)])));
+      case 'p': { int n = getnum(L, s); reg[n] = lua_getparam(L, getnum(L, s)); break; }
+      case '=': lua_setglobal(L, getname(L, s)); break;
+      case 's': lua_pushstring(L, getname(L, s)); break;
+      case 'o': lua_pushobject(L, reg[getnum(L, s)]); break;
+      case 'f': lua_call(L, getname(L, s)); break;
+      case 'i': reg[getnum(L, s)] = lua_gettable(L); break;
+      case 'I': reg[getnum(L, s)] = lua_rawgettable(L); break;
+      case 't': lua_settable(L); break;
+      case 'T': lua_rawsettable(L); break;
+      case 'N' : lua_pushstring(L, lua_nextvar(L, lua_getstring(L, reg[getnum(L, s)])));
                  break;
-      case 'n' : { int n=getnum(s);
-                   n=lua_next(reg[n], (int)lua_getnumber(reg[getnum(s)]));
-                   lua_pushnumber(n); break;
+      case 'n' : { int n=getnum(L, s);
+                   n=lua_next(L, reg[n], (int)lua_getnumber(L, reg[getnum(L, s)]));
+                   lua_pushnumber(L, n); break;
                  }
-      case 'q' : { int n1=getnum(s); int n2=getnum(s);
-                   lua_pushnumber(lua_equalobj(reg[n1], reg[n2]));
+      case 'q' : { int n1=getnum(L, s); int n2=getnum(L, s);
+                   lua_pushnumber(L, lua_equalobj(L, reg[n1], reg[n2]));
                    break;
                  }
-      default: luaL_verror("unknown command in `testC': %c", *(s-1));
+      default: luaL_verror(L, "unknown command in `testC': %c", *(s-1));
     }
   if (*s == 0) return;
-  if (*s++ != ' ') lua_error("missing ` ' between commands in `testC'");
+  if (*s++ != ' ') lua_error(L, "missing ` ' between commands in `testC'");
   }
 }
 
@@ -804,15 +806,12 @@ static const struct luaL_reg builtin_funcs[] = {
 };
 
 
-#define INTFUNCSIZE (sizeof(builtin_funcs)/sizeof(builtin_funcs[0]))
-
-
-void luaB_predefine (void) {
+void luaB_predefine (lua_State *L) {
   /* pre-register mem error messages, to avoid loop when error arises */
-  luaS_newfixedstring(tableEM);
-  luaS_newfixedstring(memEM);
-  luaL_openlib(builtin_funcs, (sizeof(builtin_funcs)/sizeof(builtin_funcs[0])));
-  lua_pushstring(LUA_VERSION);
-  lua_setglobal("_VERSION");
+  luaS_newfixedstring(L, tableEM);
+  luaS_newfixedstring(L, memEM);
+  luaL_openlib(L, builtin_funcs, (sizeof(builtin_funcs)/sizeof(builtin_funcs[0])));
+  lua_pushstring(L, LUA_VERSION);
+  lua_setglobal(L, "_VERSION");
 }
 

+ 3 - 2
lbuiltin.h

@@ -1,5 +1,5 @@
 /*
-** $Id: $
+** $Id: lbuiltin.h,v 1.1 1997/09/16 19:25:59 roberto Exp roberto $
 ** Built-in functions
 ** See Copyright Notice in lua.h
 */
@@ -7,8 +7,9 @@
 #ifndef lbuiltin_h
 #define lbuiltin_h
 
+#include "lua.h"
 
-void luaB_predefine (void);
+void luaB_predefine (lua_State *L);
 
 
 #endif

+ 94 - 92
ldblib.c

@@ -1,5 +1,5 @@
 /*
-** $Id: ldblib.c,v 1.5 1999/03/04 21:17:26 roberto Exp roberto $
+** $Id: ldblib.c,v 1.6 1999/08/16 20:52:00 roberto Exp roberto $
 ** Interface from Lua to its debug API
 ** See Copyright Notice in lua.h
 */
@@ -8,6 +8,8 @@
 #include <stdlib.h>
 #include <string.h>
 
+#define LUA_REENTRANT
+
 #include "lauxlib.h"
 #include "lua.h"
 #include "luadebug.h"
@@ -15,129 +17,129 @@
 
 
 
-static void settabss (lua_Object t, const char *i, const char *v) {
-  lua_pushobject(t);
-  lua_pushstring(i);
-  lua_pushstring(v);
-  lua_settable();
+static void settabss (lua_State *L, lua_Object t, const char *i, const char *v) {
+  lua_pushobject(L, t);
+  lua_pushstring(L, i);
+  lua_pushstring(L, v);
+  lua_settable(L);
 }
 
 
-static void settabsi (lua_Object t, const char *i, int v) {
-  lua_pushobject(t);
-  lua_pushstring(i);
-  lua_pushnumber(v);
-  lua_settable();
+static void settabsi (lua_State *L, lua_Object t, const char *i, int v) {
+  lua_pushobject(L, t);
+  lua_pushstring(L, i);
+  lua_pushnumber(L, v);
+  lua_settable(L);
 }
 
 
-static lua_Object getfuncinfo (lua_Object func) {
-  lua_Object result = lua_createtable();
+static lua_Object getfuncinfo (lua_State *L, lua_Object func) {
+  lua_Object result = lua_createtable(L);
   const char *str;
   int line;
-  lua_funcinfo(func, &str, &line);
+  lua_funcinfo(L, func, &str, &line);
   if (line == -1)  /* C function? */
-    settabss(result, "kind", "C");
+    settabss(L, result, "kind", "C");
   else if (line == 0) {  /* "main"? */
-      settabss(result, "kind", "chunk");
-      settabss(result, "source", str);
+      settabss(L, result, "kind", "chunk");
+      settabss(L, result, "source", str);
     }
   else {  /* Lua function */
-    settabss(result, "kind", "Lua");
-    settabsi(result, "def_line", line);
-    settabss(result, "source", str);
+    settabss(L, result, "kind", "Lua");
+    settabsi(L, result, "def_line", line);
+    settabss(L, result, "source", str);
   }
   if (line != 0) {  /* is it not a "main"? */
-    const char *kind = lua_getobjname(func, &str);
+    const char *kind = lua_getobjname(L, func, &str);
     if (*kind) {
-      settabss(result, "name", str);
-      settabss(result, "where", kind);
+      settabss(L, result, "name", str);
+      settabss(L, result, "where", kind);
     }
   }
   return result;
 }
 
 
-static void getstack (void) {
-  lua_Object func = lua_stackedfunction(luaL_check_int(1));
+static void getstack (lua_State *L) {
+  lua_Object func = lua_stackedfunction(L, luaL_check_int(L, 1));
   if (func == LUA_NOOBJECT)  /* level out of range? */
     return;
   else {
-    lua_Object result = getfuncinfo(func);
-    int currline = lua_currentline(func);
+    lua_Object result = getfuncinfo(L, func);
+    int currline = lua_currentline(L, func);
     if (currline > 0)
-      settabsi(result, "current", currline);
-    lua_pushobject(result);
-    lua_pushstring("func");
-    lua_pushobject(func);
-    lua_settable();  /* result.func = func */
-    lua_pushobject(result);
+      settabsi(L, result, "current", currline);
+    lua_pushobject(L, result);
+    lua_pushstring(L, "func");
+    lua_pushobject(L, func);
+    lua_settable(L);  /* result.func = func */
+    lua_pushobject(L, result);
   }
 }
 
 
-static void funcinfo (void) {
-  lua_pushobject(getfuncinfo(luaL_functionarg(1)));
+static void funcinfo (lua_State *L) {
+  lua_pushobject(L, getfuncinfo(L, luaL_functionarg(L, 1)));
 }
 
 
-static int findlocal (lua_Object func, int arg) {
-  lua_Object v = lua_getparam(arg);
-  if (lua_isnumber(v))
-    return (int)lua_getnumber(v);
+static int findlocal (lua_State *L, lua_Object func, int arg) {
+  lua_Object v = lua_getparam(L, arg);
+  if (lua_isnumber(L, v))
+    return (int)lua_getnumber(L, v);
   else {
-    const char *name = luaL_check_string(arg);
+    const char *name = luaL_check_string(L, arg);
     int i = 0;
     int result = -1;
     const char *vname;
-    while (lua_getlocal(func, ++i, &vname) != LUA_NOOBJECT) {
+    while (lua_getlocal(L, func, ++i, &vname) != LUA_NOOBJECT) {
       if (strcmp(name, vname) == 0)
         result = i;  /* keep looping to get the last var with this name */
     }
     if (result == -1)
-      luaL_verror("no local variable `%.50s' at given level", name);
+      luaL_verror(L, "no local variable `%.50s' at given level", name);
     return result;
   }
 }
 
 
-static void getlocal (void) {
-  lua_Object func = lua_stackedfunction(luaL_check_int(1));
+static void getlocal (lua_State *L) {
+  lua_Object func = lua_stackedfunction(L, luaL_check_int(L, 1));
   lua_Object val;
   const char *name;
   if (func == LUA_NOOBJECT)  /* level out of range? */
     return;  /* return nil */
-  else if (lua_getparam(2) != LUA_NOOBJECT) {  /* 2nd argument? */
-    if ((val = lua_getlocal(func, findlocal(func, 2), &name)) != LUA_NOOBJECT) {
-      lua_pushobject(val);
-      lua_pushstring(name);
+  else if (lua_getparam(L, 2) != LUA_NOOBJECT) {  /* 2nd argument? */
+    if ((val = lua_getlocal(L, func, findlocal(L, func, 2), &name)) != LUA_NOOBJECT) {
+      lua_pushobject(L, val);
+      lua_pushstring(L, name);
     }
     /* else return nil */
   }
   else {  /* collect all locals in a table */
-    lua_Object result = lua_createtable();
+    lua_Object result = lua_createtable(L);
     int i;
     for (i=1; ;i++) {
-      if ((val = lua_getlocal(func, i, &name)) == LUA_NOOBJECT)
+      if ((val = lua_getlocal(L, func, i, &name)) == LUA_NOOBJECT)
         break;
-      lua_pushobject(result);
-      lua_pushstring(name);
-      lua_pushobject(val);
-      lua_settable();  /* result[name] = value */
+      lua_pushobject(L, result);
+      lua_pushstring(L, name);
+      lua_pushobject(L, val);
+      lua_settable(L);  /* result[name] = value */
     }
-    lua_pushobject(result);
+    lua_pushobject(L, result);
   }
 }
 
 
-static void setlocal (void) {
-  lua_Object func = lua_stackedfunction(luaL_check_int(1));
+static void setlocal (lua_State *L) {
+  lua_Object func = lua_stackedfunction(L, luaL_check_int(L, 1));
   int numvar;
-  luaL_arg_check(func != LUA_NOOBJECT, 1, "level out of range");
-  numvar = findlocal(func, 2);
-  lua_pushobject(luaL_nonnullarg(3));
-  if (!lua_setlocal(func, numvar))
-    lua_error("no such local variable");
+  luaL_arg_check(L, func != LUA_NOOBJECT, 1, "level out of range");
+  numvar = findlocal(L, func, 2);
+  lua_pushobject(L, luaL_nonnullarg(L, 3));
+  if (!lua_setlocal(L, func, numvar))
+    lua_error(L, "no such local variable");
 }
 
 
@@ -146,57 +148,57 @@ static int linehook = -1;  /* Lua reference to line hook function */
 static int callhook = -1;  /* Lua reference to call hook function */
 
 
-static void dohook (int ref) {
-  lua_LHFunction oldlinehook = lua_setlinehook(NULL);
-  lua_CHFunction oldcallhook = lua_setcallhook(NULL);
-  lua_callfunction(lua_getref(ref));
-  lua_setlinehook(oldlinehook);
-  lua_setcallhook(oldcallhook);
+static void dohook (lua_State *L, int ref) {
+  lua_LHFunction oldlinehook = lua_setlinehook(L, NULL);
+  lua_CHFunction oldcallhook = lua_setcallhook(L, NULL);
+  lua_callfunction(L, lua_getref(L, ref));
+  lua_setlinehook(L, oldlinehook);
+  lua_setcallhook(L, oldcallhook);
 }
 
 
-static void linef (int line) {
-  lua_pushnumber(line);
-  dohook(linehook);
+static void linef (lua_State *L, int line) {
+  lua_pushnumber(L, line);
+  dohook(L, linehook);
 }
 
 
-static void callf (lua_Function func, const char *file, int line) {
+static void callf (lua_State *L, lua_Function func, const char *file, int line) {
   if (func != LUA_NOOBJECT) {
-    lua_pushobject(func);
-    lua_pushstring(file);
-    lua_pushnumber(line);
+    lua_pushobject(L, func);
+    lua_pushstring(L, file);
+    lua_pushnumber(L, line);
   }
-  dohook(callhook);
+  dohook(L, callhook);
 }
 
 
-static void setcallhook (void) {
-  lua_Object f = lua_getparam(1);
-  lua_unref(callhook);
+static void setcallhook (lua_State *L) {
+  lua_Object f = lua_getparam(L, 1);
+  lua_unref(L, callhook);
   if (f == LUA_NOOBJECT) {
     callhook = -1;
-    lua_setcallhook(NULL);
+    lua_setcallhook(L, NULL);
   }
   else {
-    lua_pushobject(f);
-    callhook = lua_ref(1);
-    lua_setcallhook(callf);
+    lua_pushobject(L, f);
+    callhook = lua_ref(L, 1);
+    lua_setcallhook(L, callf);
   }
 }
 
 
-static void setlinehook (void) {
-  lua_Object f = lua_getparam(1);
-  lua_unref(linehook);
+static void setlinehook (lua_State *L) {
+  lua_Object f = lua_getparam(L, 1);
+  lua_unref(L, linehook);
   if (f == LUA_NOOBJECT) {
     linehook = -1;
-    lua_setlinehook(NULL);
+    lua_setlinehook(L, NULL);
   }
   else {
-    lua_pushobject(f);
-    linehook = lua_ref(1);
-    lua_setlinehook(linef);
+    lua_pushobject(L, f);
+    linehook = lua_ref(L, 1);
+    lua_setlinehook(L, linef);
   }
 }
 
@@ -211,7 +213,7 @@ static const struct luaL_reg dblib[] = {
 };
 
 
-void lua_dblibopen (void) {
-  luaL_openlib(dblib, (sizeof(dblib)/sizeof(dblib[0])));
+void lua_dblibopen (lua_State *L) {
+  luaL_openlib(L, dblib, (sizeof(dblib)/sizeof(dblib[0])));
 }
 

+ 64 - 63
ldo.c

@@ -1,5 +1,5 @@
 /*
-** $Id: ldo.c,v 1.50 1999/10/14 19:46:57 roberto Exp roberto $
+** $Id: ldo.c,v 1.51 1999/11/04 17:22:26 roberto Exp roberto $
 ** Stack and Call structure of Lua
 ** See Copyright Notice in lua.h
 */
@@ -9,6 +9,8 @@
 #include <stdlib.h>
 #include <string.h>
 
+#define LUA_REENTRANT
+
 #include "lauxlib.h"
 #include "ldo.h"
 #include "lgc.h"
@@ -41,26 +43,26 @@
 #endif
 
 
-void luaD_init (void) {
-  L->stack.stack = luaM_newvector(STACK_UNIT, TObject);
+void luaD_init (lua_State *L) {
+  L->stack.stack = luaM_newvector(L, STACK_UNIT, TObject);
   L->stack.top = L->stack.stack;
   L->stack.last = L->stack.stack+(STACK_UNIT-1);
 }
 
 
-void luaD_checkstack (int n) {
+void luaD_checkstack (lua_State *L, int n) {
   struct Stack *S = &L->stack;
   if (S->last-S->top <= n) {
     StkId top = S->top-S->stack;
     int stacksize = (S->last-S->stack)+STACK_UNIT+n;
-    luaM_reallocvector(S->stack, stacksize, TObject);
+    luaM_reallocvector(L, S->stack, stacksize, TObject);
     S->last = S->stack+(stacksize-1);
     S->top = S->stack + top;
     if (stacksize >= STACK_LIMIT) {  /* stack overflow? */
-      if (lua_stackedfunction(100) == LUA_NOOBJECT)  /* 100 funcs on stack? */
-        lua_error("Lua2C - C2Lua overflow"); /* doesn't look like a rec. loop */
+      if (lua_stackedfunction(L, 100) == LUA_NOOBJECT)  /* 100 funcs on stack? */
+        lua_error(L, "Lua2C - C2Lua overflow"); /* doesn't look like a rec. loop */
       else
-        lua_error("stack size overflow");
+        lua_error(L, "stack size overflow");
     }
   }
 }
@@ -69,12 +71,12 @@ void luaD_checkstack (int n) {
 /*
 ** Adjust stack. Set top to the given value, pushing NILs if needed.
 */
-void luaD_adjusttop (StkId newtop) {
+void luaD_adjusttop (lua_State *L, StkId newtop) {
   int diff = newtop-(L->stack.top-L->stack.stack);
   if (diff <= 0)
     L->stack.top += diff;
   else {
-    luaD_checkstack(diff);
+    luaD_checkstack(L, diff);
     while (diff--)
       ttype(L->stack.top++) = LUA_T_NIL;
   }
@@ -84,35 +86,34 @@ void luaD_adjusttop (StkId newtop) {
 /*
 ** Open a hole below "nelems" from the L->stack.top.
 */
-void luaD_openstack (int nelems) {
+void luaD_openstack (lua_State *L, int nelems) {
   luaO_memup(L->stack.top-nelems+1, L->stack.top-nelems,
              nelems*sizeof(TObject));
   incr_top;
 }
 
 
-void luaD_lineHook (int line) {
+void luaD_lineHook (lua_State *L, int line) {
   struct C_Lua_Stack oldCLS = L->Cstack;
   StkId old_top = L->Cstack.lua2C = L->Cstack.base = L->stack.top-L->stack.stack;
   L->Cstack.num = 0;
-  (*L->linehook)(line);
+  (*L->linehook)(L, line);
   L->stack.top = L->stack.stack+old_top;
   L->Cstack = oldCLS;
 }
 
 
-void luaD_callHook (StkId base, const TProtoFunc *tf, int isreturn) {
+void luaD_callHook (lua_State *L, StkId base, const TProtoFunc *tf, int isreturn) {
   struct C_Lua_Stack oldCLS = L->Cstack;
   StkId old_top = L->Cstack.lua2C = L->Cstack.base = L->stack.top-L->stack.stack;
   L->Cstack.num = 0;
   if (isreturn)
-    (*L->callhook)(LUA_NOOBJECT, "(return)", 0);
+    (*L->callhook)(L, LUA_NOOBJECT, "(return)", 0);
   else {
     TObject *f = L->stack.stack+base-1;
     if (tf)
-      (*L->callhook)(Ref(f), tf->source->str, tf->lineDefined);
-    else
-      (*L->callhook)(Ref(f), "(C)", -1);
+      (*L->callhook)(L, Ref(L, f), tf->source->str, tf->lineDefined);
+    else (*L->callhook)(L, Ref(L, f), "(C)", -1);
   }
   L->stack.top = L->stack.stack+old_top;
   L->Cstack = oldCLS;
@@ -124,7 +125,7 @@ void luaD_callHook (StkId base, const TProtoFunc *tf, int isreturn) {
 ** Cstack.num is the number of arguments; Cstack.lua2C points to the
 ** first argument. Returns an index to the first result from C.
 */
-static StkId callC (lua_CFunction f, StkId base) {
+static StkId callC (lua_State *L, lua_CFunction f, StkId base) {
   struct C_Lua_Stack *cls = &L->Cstack;
   struct C_Lua_Stack oldCLS = *cls;
   StkId firstResult;
@@ -133,35 +134,35 @@ static StkId callC (lua_CFunction f, StkId base) {
   cls->lua2C = base;
   cls->base = base+numarg;  /* == top-stack */
   if (L->callhook)
-    luaD_callHook(base, NULL, 0);
-  (*f)();  /* do the actual call */
+    luaD_callHook(L, base, NULL, 0);
+  (*f)(L);  /* do the actual call */
   if (L->callhook)  /* func may have changed callhook */
-    luaD_callHook(base, NULL, 1);
+    luaD_callHook(L, base, NULL, 1);
   firstResult = cls->base;
   *cls = oldCLS;
   return firstResult;
 }
 
 
-static StkId callCclosure (const struct Closure *cl,
+static StkId callCclosure (lua_State *L, const struct Closure *cl,
                            lua_CFunction f, StkId base) {
   TObject *pbase;
   int nup = cl->nelems;  /* number of upvalues */
-  luaD_checkstack(nup);
+  luaD_checkstack(L, nup);
   pbase = L->stack.stack+base;  /* care: previous call may change this */
   /* open space for upvalues as extra arguments */
   luaO_memup(pbase+nup, pbase, (L->stack.top-pbase)*sizeof(TObject));
   /* copy upvalues into stack */
   memcpy(pbase, cl->consts+1, nup*sizeof(TObject));
   L->stack.top += nup;
-  return callC(f, base);
+  return callC(L, f, base);
 }
 
 
-void luaD_callTM (const TObject *f, int nParams, int nResults) {
-  luaD_openstack(nParams);
+void luaD_callTM (lua_State *L, const TObject *f, int nParams, int nResults) {
+  luaD_openstack(L, nParams);
   *(L->stack.top-nParams-1) = *f;
-  luaD_calln(nParams, nResults);
+  luaD_calln(L, nParams, nResults);
 }
 
 
@@ -172,7 +173,7 @@ void luaD_callTM (const TObject *f, int nParams, int nResults) {
 ** When returns, the results are on the stack, between [top-nArgs-1,top).
 ** The number of results is nResults, unless nResults=MULT_RET.
 */
-void luaD_calln (int nArgs, int nResults) {
+void luaD_calln (lua_State *L, int nArgs, int nResults) {
   struct Stack *S = &L->stack;  /* to optimize */
   StkId base = (S->top-S->stack)-nArgs;
   TObject *func = S->stack+base-1;
@@ -181,27 +182,27 @@ void luaD_calln (int nArgs, int nResults) {
   switch (ttype(func)) {
     case LUA_T_CPROTO:
       ttype(func) = LUA_T_CMARK;
-      firstResult = callC(fvalue(func), base);
+      firstResult = callC(L, fvalue(func), base);
       break;
     case LUA_T_PROTO:
       ttype(func) = LUA_T_PMARK;
-      firstResult = luaV_execute(NULL, tfvalue(func), base);
+      firstResult = luaV_execute(L, NULL, tfvalue(func), base);
       break;
     case LUA_T_CLOSURE: {
       Closure *c = clvalue(func);
       TObject *proto = c->consts;
       ttype(func) = LUA_T_CLMARK;
       firstResult = (ttype(proto) == LUA_T_CPROTO) ?
-                       callCclosure(c, fvalue(proto), base) :
-                       luaV_execute(c, tfvalue(proto), base);
+                       callCclosure(L, c, fvalue(proto), base) :
+                       luaV_execute(L, c, tfvalue(proto), base);
       break;
     }
     default: { /* func is not a function */
       /* Check the tag method for invalid functions */
-      const TObject *im = luaT_getimbyObj(func, IM_FUNCTION);
+      const TObject *im = luaT_getimbyObj(L, func, IM_FUNCTION);
       if (ttype(im) == LUA_T_NIL)
-        lua_error("call expression not a function");
-      luaD_callTM(im, (S->top-S->stack)-(base-1), nResults);
+        lua_error(L, "call expression not a function");
+      luaD_callTM(L, im, (S->top-S->stack)-(base-1), nResults);
       return;
     }
   }
@@ -209,7 +210,7 @@ void luaD_calln (int nArgs, int nResults) {
   if (nResults == MULT_RET)
     nResults = (S->top-S->stack)-firstResult;
   else
-    luaD_adjusttop(firstResult+nResults);
+    luaD_adjusttop(L, firstResult+nResults);
   /* move results to base-1 (to erase parameters and function) */
   base--;
   for (i=0; i<nResults; i++)
@@ -218,26 +219,26 @@ void luaD_calln (int nArgs, int nResults) {
 }
 
 
-static void message (const char *s) {
-  const TObject *em = &(luaS_assertglobalbyname("_ERRORMESSAGE")->value);
+static void message (lua_State *L, const char *s) {
+  const TObject *em = &(luaS_assertglobalbyname(L, "_ERRORMESSAGE")->value);
   if (ttype(em) == LUA_T_PROTO || ttype(em) == LUA_T_CPROTO ||
       ttype(em) == LUA_T_CLOSURE) {
     *L->stack.top = *em;
     incr_top;
-    lua_pushstring(s);
-    luaD_calln(1, 0);
+    lua_pushstring(L, s);
+    luaD_calln(L, 1, 0);
   }
 }
 
 /*
 ** Reports an error, and jumps up to the available recover label
 */
-void lua_error (const char *s) {
-  if (s) message(s);
+void lua_error (lua_State *L, const char *s) {
+  if (s) message(L, s);
   if (L->errorJmp)
     longjmp(L->errorJmp->b, 1);
   else {
-    message("exit(1). Unable to recover.\n");
+    message(L, "exit(1). Unable to recover.\n");
     exit(1);
   }
 }
@@ -247,7 +248,7 @@ void lua_error (const char *s) {
 ** Execute a protected call. Assumes that function is at L->Cstack.base and
 ** parameters are on top of it. Leave nResults on the stack.
 */
-int luaD_protectedrun (void) {
+int luaD_protectedrun (lua_State *L) {
   volatile struct C_Lua_Stack oldCLS = L->Cstack;
   struct lua_longjmp myErrorJmp;
   volatile int status;
@@ -255,7 +256,7 @@ int luaD_protectedrun (void) {
   L->errorJmp = &myErrorJmp;
   if (setjmp(myErrorJmp.b) == 0) {
     StkId base = L->Cstack.base;
-    luaD_calln((L->stack.top-L->stack.stack)-base-1, MULT_RET);
+    luaD_calln(L, (L->stack.top-L->stack.stack)-base-1, MULT_RET);
     L->Cstack.lua2C = base;  /* position of the new results */
     L->Cstack.num = (L->stack.top-L->stack.stack) - base;
     L->Cstack.base = base + L->Cstack.num;  /* incorporate results on stack */
@@ -274,7 +275,7 @@ int luaD_protectedrun (void) {
 /*
 ** returns 0 = chunk loaded; 1 = error; 2 = no more chunks to load
 */
-static int protectedparser (ZIO *z, int bin) {
+static int protectedparser (lua_State *L, ZIO *z, int bin) {
   volatile struct C_Lua_Stack oldCLS = L->Cstack;
   struct lua_longjmp myErrorJmp;
   volatile int status;
@@ -282,7 +283,7 @@ static int protectedparser (ZIO *z, int bin) {
   struct lua_longjmp *volatile oldErr = L->errorJmp;
   L->errorJmp = &myErrorJmp;
   if (setjmp(myErrorJmp.b) == 0) {
-    tf = bin ? luaU_undump1(z) : luaY_parser(z);
+    tf = bin ? luaU_undump1(L, z) : luaY_parser(L, z);
     status = 0;
   }
   else {  /* an error occurred: restore L->Cstack and L->stack.top */
@@ -294,26 +295,26 @@ static int protectedparser (ZIO *z, int bin) {
   L->errorJmp = oldErr;
   if (status) return 1;  /* error code */
   if (tf == NULL) return 2;  /* 'natural' end */
-  luaD_adjusttop(L->Cstack.base+1);  /* one slot for the pseudo-function */
+  luaD_adjusttop(L, L->Cstack.base+1);  /* one slot for the pseudo-function */
   L->stack.stack[L->Cstack.base].ttype = LUA_T_PROTO;
   L->stack.stack[L->Cstack.base].value.tf = tf;
-  luaV_closure(0);
+  luaV_closure(L, 0);
   return 0;
 }
 
 
-static int do_main (ZIO *z, int bin) {
+static int do_main (lua_State *L, ZIO *z, int bin) {
   int status;
   int debug = L->debug;  /* save debug status */
   do {
-    long old_blocks = (luaC_checkGC(), L->nblocks);
-    status = protectedparser(z, bin);
+    long old_blocks = (luaC_checkGC(L), L->nblocks);
+    status = protectedparser(L, z, bin);
     if (status == 1) return 1;  /* error */
     else if (status == 2) return 0;  /* 'natural' end */
     else {
       unsigned long newelems2 = 2*(L->nblocks-old_blocks);
       L->GCthreshold += newelems2;
-      status = luaD_protectedrun();
+      status = luaD_protectedrun(L);
       L->GCthreshold -= newelems2;
     }
   } while (bin && status == 0);
@@ -322,19 +323,19 @@ static int do_main (ZIO *z, int bin) {
 }
 
 
-void luaD_gcIM (const TObject *o) {
-  const TObject *im = luaT_getimbyObj(o, IM_GC);
+void luaD_gcIM (lua_State *L, const TObject *o) {
+  const TObject *im = luaT_getimbyObj(L, o, IM_GC);
   if (ttype(im) != LUA_T_NIL) {
     *L->stack.top = *o;
     incr_top;
-    luaD_callTM(im, 1, 0);
+    luaD_callTM(L, im, 1, 0);
   }
 }
 
 
 #define	MAXFILENAME	260	/* maximum part of a file name kept */
 
-int lua_dofile (const char *filename) {
+int lua_dofile (lua_State *L, const char *filename) {
   ZIO z;
   int status;
   int c;
@@ -350,22 +351,22 @@ int lua_dofile (const char *filename) {
     f = freopen(filename, "rb", f);  /* set binary mode */
   luaL_filesource(source, filename, sizeof(source));
   luaZ_Fopen(&z, f, source);
-  status = do_main(&z, bin);
+  status = do_main(L, &z, bin);
   if (f != stdin)
     fclose(f);
   return status;
 }
 
 
-int lua_dostring (const char *str) {
-  return lua_dobuffer(str, strlen(str), str);
+int lua_dostring (lua_State *L, const char *str) {
+  return lua_dobuffer(L, str, strlen(str), str);
 }
 
 
-int lua_dobuffer (const char *buff, int size, const char *name) {
+int lua_dobuffer (lua_State *L, const char *buff, int size, const char *name) {
   ZIO z;
   if (!name) name = "?";
   luaZ_mopen(&z, buff, size, name);
-  return do_main(&z, buff[0]==ID_CHUNK);
+  return do_main(L, &z, buff[0]==ID_CHUNK);
 }
 

+ 14 - 14
ldo.h

@@ -1,5 +1,5 @@
 /*
-** $Id: ldo.h,v 1.8 1999/10/04 17:51:04 roberto Exp roberto $
+** $Id: ldo.h,v 1.9 1999/10/14 19:46:57 roberto Exp roberto $
 ** Stack and Call structure of Lua
 ** See Copyright Notice in lua.h
 */
@@ -20,26 +20,26 @@
 ** macro to increment stack top.
 ** There must be always an empty slot at the L->stack.top
 */
-#define incr_top { if (L->stack.top >= L->stack.last) luaD_checkstack(1); \
+#define incr_top { if (L->stack.top >= L->stack.last) luaD_checkstack(L, 1); \
                    L->stack.top++; }
 
 
 /* macros to convert from lua_Object to (TObject *) and back */
 
-#define Address(lo)     ((lo)+L->stack.stack-1)
-#define Ref(st)         ((st)-L->stack.stack+1)
+#define Address(L, lo)     ((lo)+L->stack.stack-1)
+#define Ref(L, st)         ((st)-L->stack.stack+1)
 
 
-void luaD_init (void);
-void luaD_adjusttop (StkId newtop);
-void luaD_openstack (int nelems);
-void luaD_lineHook (int line);
-void luaD_callHook (StkId base, const TProtoFunc *tf, int isreturn);
-void luaD_calln (int nArgs, int nResults);
-void luaD_callTM (const TObject *f, int nParams, int nResults);
-int luaD_protectedrun (void);
-void luaD_gcIM (const TObject *o);
-void luaD_checkstack (int n);
+void luaD_init (lua_State *L);
+void luaD_adjusttop (lua_State *L, StkId newtop);
+void luaD_openstack (lua_State *L, int nelems);
+void luaD_lineHook (lua_State *L, int line);
+void luaD_callHook (lua_State *L, StkId base, const TProtoFunc *tf, int isreturn);
+void luaD_calln (lua_State *L, int nArgs, int nResults);
+void luaD_callTM (lua_State *L, const TObject *f, int nParams, int nResults);
+int luaD_protectedrun (lua_State *L);
+void luaD_gcIM (lua_State *L, const TObject *o);
+void luaD_checkstack (lua_State *L, int n);
 
 
 #endif

+ 20 - 18
lfunc.c

@@ -1,5 +1,5 @@
 /*
-** $Id: lfunc.c,v 1.13 1999/10/14 19:46:57 roberto Exp roberto $
+** $Id: lfunc.c,v 1.14 1999/11/10 15:39:35 roberto Exp roberto $
 ** Auxiliary functions to manipulate prototypes and closures
 ** See Copyright Notice in lua.h
 */
@@ -7,28 +7,30 @@
 
 #include <stdlib.h>
 
+#define LUA_REENTRANT
+
 #include "lfunc.h"
 #include "lmem.h"
 #include "lstate.h"
 
-#define gcsizeproto(p)	numblocks(0, sizeof(TProtoFunc))
-#define gcsizeclosure(c) numblocks(c->nelems, sizeof(Closure))
+#define gcsizeproto(L, p)	numblocks(L, 0, sizeof(TProtoFunc))
+#define gcsizeclosure(L, c) numblocks(L, c->nelems, sizeof(Closure))
 
 
 
-Closure *luaF_newclosure (int nelems) {
-  Closure *c = (Closure *)luaM_malloc(sizeof(Closure)+nelems*sizeof(TObject));
+Closure *luaF_newclosure (lua_State *L, int nelems) {
+  Closure *c = (Closure *)luaM_malloc(L, sizeof(Closure)+nelems*sizeof(TObject));
   c->next = L->rootcl;
   L->rootcl = c;
   c->marked = 0;
   c->nelems = nelems;
-  L->nblocks += gcsizeclosure(c);
+  L->nblocks += gcsizeclosure(L, c);
   return c;
 }
 
 
-TProtoFunc *luaF_newproto (void) {
-  TProtoFunc *f = luaM_new(TProtoFunc);
+TProtoFunc *luaF_newproto (lua_State *L) {
+  TProtoFunc *f = luaM_new(L, TProtoFunc);
   f->code = NULL;
   f->lineDefined = 0;
   f->source = NULL;
@@ -38,23 +40,23 @@ TProtoFunc *luaF_newproto (void) {
   f->next = L->rootproto;
   L->rootproto = f;
   f->marked = 0;
-  L->nblocks += gcsizeproto(f);
+  L->nblocks += gcsizeproto(L, f);
   return f;
 }
 
 
-void luaF_freeproto (TProtoFunc *f) {
-  L->nblocks -= gcsizeproto(f);
-  luaM_free(f->code);
-  luaM_free(f->locvars);
-  luaM_free(f->consts);
-  luaM_free(f);
+void luaF_freeproto (lua_State *L, TProtoFunc *f) {
+  L->nblocks -= gcsizeproto(L, f);
+  luaM_free(L, f->code);
+  luaM_free(L, f->locvars);
+  luaM_free(L, f->consts);
+  luaM_free(L, f);
 }
 
 
-void luaF_freeclosure (Closure *c) {
-  L->nblocks -= gcsizeclosure(c);
-  luaM_free(c);
+void luaF_freeclosure (lua_State *L, Closure *c) {
+  L->nblocks -= gcsizeclosure(L, c);
+  luaM_free(L, c);
 }
 
 

+ 5 - 5
lfunc.h

@@ -1,5 +1,5 @@
 /*
-** $Id: lfunc.h,v 1.7 1999/10/04 17:51:04 roberto Exp roberto $
+** $Id: lfunc.h,v 1.8 1999/10/14 19:46:57 roberto Exp roberto $
 ** Lua Function structures
 ** See Copyright Notice in lua.h
 */
@@ -12,10 +12,10 @@
 
 
 
-TProtoFunc *luaF_newproto (void);
-Closure *luaF_newclosure (int nelems);
-void luaF_freeproto (TProtoFunc *f);
-void luaF_freeclosure (Closure *c);
+TProtoFunc *luaF_newproto (lua_State *L);
+Closure *luaF_newclosure (lua_State *L, int nelems);
+void luaF_freeproto (lua_State *L, TProtoFunc *f);
+void luaF_freeclosure (lua_State *L, Closure *c);
 
 const char *luaF_getlocalname (const TProtoFunc *func,
                                int local_number, int line);

+ 62 - 61
lgc.c

@@ -1,9 +1,10 @@
 /*
-** $Id: lgc.c,v 1.30 1999/11/04 17:22:26 roberto Exp roberto $
+** $Id: lgc.c,v 1.31 1999/11/10 15:40:46 roberto Exp roberto $
 ** Garbage Collector
 ** See Copyright Notice in lua.h
 */
 
+#define LUA_REENTRANT
 
 #include "ldo.h"
 #include "lfunc.h"
@@ -19,91 +20,91 @@
 
 
 
-static int markobject (TObject *o);
+static int markobject (lua_State *L, TObject *o);
 
 
 /* mark a string; marks bigger than 1 cannot be changed */
-#define strmark(s)    {if ((s)->marked == 0) (s)->marked = 1;}
+#define strmark(L, s)    {if ((s)->marked == 0) (s)->marked = 1;}
 
 
 
-static void protomark (TProtoFunc *f) {
+static void protomark (lua_State *L, TProtoFunc *f) {
   if (!f->marked) {
     int i;
     f->marked = 1;
-    strmark(f->source);
+    strmark(L, f->source);
     for (i=f->nconsts-1; i>=0; i--)
-      markobject(&f->consts[i]);
+      markobject(L, &f->consts[i]);
   }
 }
 
 
-static void closuremark (Closure *f) {
+static void closuremark (lua_State *L, Closure *f) {
   if (!f->marked) {
     int i;
     f->marked = 1;
     for (i=f->nelems; i>=0; i--)
-      markobject(&f->consts[i]);
+      markobject(L, &f->consts[i]);
   }
 }
 
 
-static void hashmark (Hash *h) {
+static void hashmark (lua_State *L, Hash *h) {
   if (!h->marked) {
     int i;
     h->marked = 1;
     for (i=h->size-1; i>=0; i--) {
-      Node *n = node(h,i);
-      if (ttype(key(n)) != LUA_T_NIL) {
-        markobject(&n->key);
-        markobject(&n->val);
+      Node *n = node(L, h,i);
+      if (ttype(key(L, n)) != LUA_T_NIL) {
+        markobject(L, &n->key);
+        markobject(L, &n->val);
       }
     }
   }
 }
 
 
-static void travglobal (void) {
+static void travglobal (lua_State *L) {
   GlobalVar *gv;
   for (gv=L->rootglobal; gv; gv=gv->next) {
-    LUA_ASSERT(gv->name->u.s.gv == gv, "inconsistent global name");
+    LUA_ASSERT(L, gv->name->u.s.gv == gv, "inconsistent global name");
     if (gv->value.ttype != LUA_T_NIL) {
-      strmark(gv->name);  /* cannot collect non nil global variables */
-      markobject(&gv->value);
+      strmark(L, gv->name);  /* cannot collect non nil global variables */
+      markobject(L, &gv->value);
     }
   }
 }
 
 
-static void travstack (void) {
+static void travstack (lua_State *L) {
   StkId i;
   for (i = (L->stack.top-1)-L->stack.stack; i>=0; i--)
-    markobject(L->stack.stack+i);
+    markobject(L, L->stack.stack+i);
 }
 
 
-static void travlock (void) {
+static void travlock (lua_State *L) {
   int i;
   for (i=0; i<L->refSize; i++) {
     if (L->refArray[i].st == LOCK)
-      markobject(&L->refArray[i].o);
+      markobject(L, &L->refArray[i].o);
   }
 }
 
 
-static int markobject (TObject *o) {
+static int markobject (lua_State *L, TObject *o) {
   switch (ttype(o)) {
     case LUA_T_USERDATA:  case LUA_T_STRING:
-      strmark(tsvalue(o));
+      strmark(L, tsvalue(o));
       break;
     case LUA_T_ARRAY:
-      hashmark(avalue(o));
+      hashmark(L, avalue(o));
       break;
     case LUA_T_CLOSURE:  case LUA_T_CLMARK:
-      closuremark(o->value.cl);
+      closuremark(L, o->value.cl);
       break;
     case LUA_T_PROTO: case LUA_T_PMARK:
-      protomark(o->value.tf);
+      protomark(L, o->value.tf);
       break;
     default: break;  /* numbers, cprotos, etc */
   }
@@ -111,7 +112,7 @@ static int markobject (TObject *o) {
 }
 
 
-static void collectproto (void) {
+static void collectproto (lua_State *L) {
   TProtoFunc **p = &L->rootproto;
   TProtoFunc *next;
   while ((next = *p) != NULL) {
@@ -121,13 +122,13 @@ static void collectproto (void) {
     }
     else {
       *p = next->next;
-      luaF_freeproto(next);
+      luaF_freeproto(L, next);
     }
   }
 }
 
 
-static void collectclosure (void) {
+static void collectclosure (lua_State *L) {
   Closure **p = &L->rootcl;
   Closure *next;
   while ((next = *p) != NULL) {
@@ -137,13 +138,13 @@ static void collectclosure (void) {
     }
     else {
       *p = next->next;
-      luaF_freeclosure(next);
+      luaF_freeclosure(L, next);
     }
   }
 }
 
 
-static void collecttable (void) {
+static void collecttable (lua_State *L) {
   Hash **p = &L->roottable;
   Hash *next;
   while ((next = *p) != NULL) {
@@ -153,7 +154,7 @@ static void collecttable (void) {
     }
     else {
       *p = next->next;
-      luaH_free(next);
+      luaH_free(L, next);
     }
   }
 }
@@ -163,7 +164,7 @@ static void collecttable (void) {
 ** remove from the global list globals whose names will be collected
 ** (the global itself is freed when its name is freed)
 */
-static void clear_global_list (int limit) {
+static void clear_global_list (lua_State *L, int limit) {
   GlobalVar **p = &L->rootglobal;
   GlobalVar *next;
   while ((next = *p) != NULL) {
@@ -176,13 +177,13 @@ static void clear_global_list (int limit) {
 /*
 ** collect all elements with `marked' < `limit'.
 ** with limit=1, that means all unmarked elements;
-** with limit=MAX_INT, that means all elements (but EMPTY).
+** with limit=MAX_INT, that means all elements.
 */
-static void collectstring (int limit) {
+static void collectstring (lua_State *L, int limit) {
   TObject o;  /* to call userdata 'gc' tag method */
   int i;
   ttype(&o) = LUA_T_USERDATA;
-  clear_global_list(limit);
+  clear_global_list(L, limit);
   for (i=0; i<NUM_HASHS; i++) {  /* for each hash table */
     stringtable *tb = &L->string_root[i];
     int j;
@@ -198,74 +199,74 @@ static void collectstring (int limit) {
        else {  /* collect */
           if (next->constindex == -1) {  /* is userdata? */
             tsvalue(&o) = next;
-            luaD_gcIM(&o);
+            luaD_gcIM(L, &o);
           }
           *p = next->nexthash;
-          luaS_free(next);
+          luaS_free(L, next);
           tb->nuse--;
         }
       }
     }
     if ((tb->nuse+1)*6 < tb->size)
-      luaS_grow(tb);  /* table is too big; `grow' it to a smaller size */
+      luaS_grow(L, tb);  /* table is too big; `grow' it to a smaller size */
   }
 }
 
 
 #ifdef LUA_COMPAT_GC
-static void tableTM (void) {
+static void tableTM (lua_State *L) {
   Hash *p;
   TObject o;
   ttype(&o) = LUA_T_ARRAY;
   for (p = L->roottable; p; p = p->next) {
     if (!p->marked) {
       avalue(&o) = p;
-      luaD_gcIM(&o);
+      luaD_gcIM(L, &o);
     }
   }
 }
 #else
-#define tableTM()	/* do nothing */
+#define tableTM(L)	/* do nothing */
 #endif
 
 
 
-static void markall (void) {
-  travstack(); /* mark stack objects */
-  travglobal();  /* mark global variable values and names */
-  travlock(); /* mark locked objects */
-  luaT_travtagmethods(markobject);  /* mark tag methods */
+static void markall (lua_State *L) {
+  travstack(L); /* mark stack objects */
+  travglobal(L);  /* mark global variable values and names */
+  travlock(L); /* mark locked objects */
+  luaT_travtagmethods(L, markobject);  /* mark tag methods */
 }
 
 
-void luaC_collect (int all) {
+void luaC_collect (lua_State *L, int all) {
   L->GCthreshold *= 4;  /* to avoid GC during GC */
-  tableTM();  /* call TM for tables (if LUA_COMPAT_GC) */
-  collecttable();
-  collectstring(all?MAX_INT:1);
-  collectproto();
-  collectclosure();
+  tableTM(L);  /* call TM for tables (if LUA_COMPAT_GC) */
+  collecttable(L);
+  collectstring(L, all?MAX_INT:1);
+  collectproto(L);
+  collectclosure(L);
 }
 
 
-long lua_collectgarbage (long limit) {
+long lua_collectgarbage (lua_State *L, long limit) {
   unsigned long recovered = L->nblocks;  /* to subtract nblocks after gc */
-  markall();
-  luaR_invalidaterefs();
-  luaC_collect(0);
-  luaD_gcIM(&luaO_nilobject);  /* GC tag method for nil (signal end of GC) */
+  markall(L);
+  luaR_invalidaterefs(L);
+  luaC_collect(L, 0);
+  luaD_gcIM(L, &luaO_nilobject);  /* GC tag method for nil (signal end of GC) */
   recovered = recovered - L->nblocks;
   L->GCthreshold = (limit == 0) ? 2*L->nblocks : L->nblocks+limit;
   if (L->Mbuffsize > L->Mbuffnext*4) {  /* is buffer too big? */
     L->Mbuffsize /= 2;  /* still larger than Mbuffnext*2 */
-    luaM_reallocvector(L->Mbuffer, L->Mbuffsize, char);
+    luaM_reallocvector(L, L->Mbuffer, L->Mbuffsize, char);
   }
   return recovered;
 }
 
 
-void luaC_checkGC (void) {
+void luaC_checkGC (lua_State *L) {
   if (L->nblocks >= L->GCthreshold)
-    lua_collectgarbage(0);
+    lua_collectgarbage(L, 0);
 }
 

+ 3 - 3
lgc.h

@@ -1,5 +1,5 @@
 /*
-** $Id: lgc.h,v 1.5 1999/08/16 20:52:00 roberto Exp roberto $
+** $Id: lgc.h,v 1.6 1999/10/04 17:51:04 roberto Exp roberto $
 ** Garbage Collector
 ** See Copyright Notice in lua.h
 */
@@ -11,8 +11,8 @@
 #include "lobject.h"
 
 
-void luaC_checkGC (void);
-void luaC_collect (int all);
+void luaC_checkGC (lua_State *L);
+void luaC_collect (lua_State *L, int all);
 
 
 #endif

+ 8 - 6
linit.c

@@ -1,17 +1,19 @@
 /*
-** $Id: linit.c,v 1.1 1999/01/08 16:47:44 roberto Exp $
+** $Id: linit.c,v 1.1 1999/01/08 16:49:32 roberto Exp roberto $
 ** Initialization of libraries for lua.c
 ** See Copyright Notice in lua.h
 */
 
+#define LUA_REENTRANT
+
 #include "lua.h"
 #include "lualib.h"
 
 
-void lua_userinit (void) {
-  lua_iolibopen();
-  lua_strlibopen();
-  lua_mathlibopen();
-  lua_dblibopen();
+void lua_userinit (lua_State *L) {
+  lua_iolibopen(L);
+  lua_strlibopen(L);
+  lua_mathlibopen(L);
+  lua_dblibopen(L);
 }
 

+ 182 - 180
liolib.c

@@ -1,5 +1,5 @@
 /*
-** $Id: liolib.c,v 1.49 1999/10/26 11:00:12 roberto Exp roberto $
+** $Id: liolib.c,v 1.50 1999/11/09 17:59:35 roberto Exp roberto $
 ** Standard I/O (and system) library
 ** See Copyright Notice in lua.h
 */
@@ -12,6 +12,8 @@
 #include <string.h>
 #include <time.h>
 
+#define LUA_REENTRANT
+
 #include "lauxlib.h"
 #include "lua.h"
 #include "luadebug.h"
@@ -22,7 +24,7 @@
 #include <locale.h>
 #else
 /* no support for locale and for strerror: fake them */
-#define setlocale(a,b)	0
+#define setlocale(a,b)	((void)a, strcmp((b),"C")==0?"C":NULL)
 #define LC_ALL		0
 #define LC_COLLATE	0
 #define LC_CTYPE	0
@@ -37,7 +39,7 @@
 
 #define FIRSTARG	2  /* 1st is upvalue */
 
-#define CLOSEDTAG(tag)	((tag)-1)  /* assume that CLOSEDTAG = iotag-1 */
+#define CLOSEDTAG(L, tag)	((tag)-1)  /* assume that CLOSEDTAG = iotag-1 */
 
 
 #define FINPUT		"_INPUT"
@@ -47,22 +49,22 @@
 #ifdef POPEN
 /* FILE *popen();
 int pclose(); */
-#define CLOSEFILE(f)    ((pclose(f) == -1) ? fclose(f) : 0)
+#define CLOSEFILE(L, f)    ((pclose(f) == -1) ? fclose(f) : 0)
 #else
 /* no support for popen */
 #define popen(x,y) NULL  /* that is, popen always fails */
-#define CLOSEFILE(f)    (fclose(f))
+#define CLOSEFILE(L, f)    (fclose(f))
 #endif
 
 
 
-static void pushresult (int i) {
+static void pushresult (lua_State *L, int i) {
   if (i)
-    lua_pushuserdata(NULL);
+    lua_pushuserdata(L, NULL);
   else {
-    lua_pushnil();
-    lua_pushstring(strerror(errno));
-    lua_pushnumber(errno);
+    lua_pushnil(L);
+    lua_pushstring(L, strerror(errno));
+    lua_pushnumber(L, errno);
   }
 }
 
@@ -73,144 +75,144 @@ static void pushresult (int i) {
 ** =======================================================
 */
 
-static int gettag (void) {
-  return (int)lua_getnumber(lua_getparam(IOTAG));
+static int gettag (lua_State *L) {
+  return (int)lua_getnumber(L, lua_getparam(L, IOTAG));
 }
 
 
-static int ishandle (lua_Object f) {
-  if (lua_isuserdata(f)) {
-    int tag = gettag();
-    if (lua_tag(f) == CLOSEDTAG(tag))
-      lua_error("cannot access a closed file");
-    return lua_tag(f) == tag;
+static int ishandle (lua_State *L, lua_Object f) {
+  if (lua_isuserdata(L, f)) {
+    int tag = gettag(L);
+    if (lua_tag(L, f) == CLOSEDTAG(L, tag))
+      lua_error(L, "cannot access a closed file");
+    return lua_tag(L, f) == tag;
   }
   else return 0;
 }
 
 
-static FILE *getfilebyname (const char *name) {
-  lua_Object f = lua_rawgetglobal(name);
-  if (!ishandle(f))
-      luaL_verror("global variable `%.50s' is not a file handle", name);
-  return lua_getuserdata(f);
+static FILE *getfilebyname (lua_State *L, const char *name) {
+  lua_Object f = lua_rawgetglobal(L, name);
+  if (!ishandle(L, f))
+      luaL_verror(L, "global variable `%.50s' is not a file handle", name);
+  return lua_getuserdata(L, f);
 }
 
 
-static FILE *getfile (int arg) {
-  lua_Object f = lua_getparam(arg);
-  return (ishandle(f)) ? lua_getuserdata(f) : NULL;
+static FILE *getfile (lua_State *L, int arg) {
+  lua_Object f = lua_getparam(L, arg);
+  return (ishandle(L, f)) ? lua_getuserdata(L, f) : NULL;
 }
 
 
-static FILE *getnonullfile (int arg) {
-  FILE *f = getfile(arg);
-  luaL_arg_check(f, arg, "invalid file handle");
+static FILE *getnonullfile (lua_State *L, int arg) {
+  FILE *f = getfile(L, arg);
+  luaL_arg_check(L, f, arg, "invalid file handle");
   return f;
 }
 
 
-static FILE *getfileparam (const char *name, int *arg) {
-  FILE *f = getfile(*arg);
+static FILE *getfileparam (lua_State *L, const char *name, int *arg) {
+  FILE *f = getfile(L, *arg);
   if (f) {
     (*arg)++;
     return f;
   }
   else
-    return getfilebyname(name);
+    return getfilebyname(L, name);
 }
 
 
-static int closefile (FILE *f) {
+static int closefile (lua_State *L, FILE *f) {
   if (f == stdin || f == stdout)
     return 1;
   else {
-    int tag = gettag();
-    lua_pushusertag(f, tag);
-    lua_settag(CLOSEDTAG(tag));
-    return (CLOSEFILE(f) == 0);
+    int tag = gettag(L);
+    lua_pushusertag(L, f, tag);
+    lua_settag(L, CLOSEDTAG(L, tag));
+    return (CLOSEFILE(L, f) == 0);
   }
 }
 
 
-static void io_close (void) {
-  pushresult(closefile(getnonullfile(FIRSTARG)));
+static void io_close (lua_State *L) {
+  pushresult(L, closefile(L, getnonullfile(L, FIRSTARG)));
 }
 
 
-static void gc_close (void) {
-  FILE *f = getnonullfile(FIRSTARG);
+static void gc_close (lua_State *L) {
+  FILE *f = getnonullfile(L, FIRSTARG);
   if (f != stdin && f != stdout && f != stderr) {
-    CLOSEFILE(f);
+    CLOSEFILE(L, f);
   }
 }
 
 
-static void io_open (void) {
-  FILE *f = fopen(luaL_check_string(FIRSTARG), luaL_check_string(FIRSTARG+1));
-  if (f) lua_pushusertag(f, gettag());
-  else pushresult(0);
+static void io_open (lua_State *L) {
+  FILE *f = fopen(luaL_check_string(L, FIRSTARG), luaL_check_string(L, FIRSTARG+1));
+  if (f) lua_pushusertag(L, f, gettag(L));
+  else pushresult(L, 0);
 }
 
 
-static void setfile (FILE *f, const char *name, int tag) {
-  lua_pushusertag(f, tag);
-  lua_setglobal(name);
+static void setfile (lua_State *L, FILE *f, const char *name, int tag) {
+  lua_pushusertag(L, f, tag);
+  lua_setglobal(L, name);
 }
 
 
-static void setreturn (FILE *f, const char *name) {
+static void setreturn (lua_State *L, FILE *f, const char *name) {
   if (f == NULL)
-    pushresult(0);
+    pushresult(L, 0);
   else {
-    int tag = gettag();
-    setfile(f, name, tag);
-    lua_pushusertag(f, tag);
+    int tag = gettag(L);
+    setfile(L, f, name, tag);
+    lua_pushusertag(L, f, tag);
   }
 }
 
 
-static void io_readfrom (void) {
+static void io_readfrom (lua_State *L) {
   FILE *current;
-  lua_Object f = lua_getparam(FIRSTARG);
+  lua_Object f = lua_getparam(L, FIRSTARG);
   if (f == LUA_NOOBJECT) {
-    if (closefile(getfilebyname(FINPUT)))
+    if (closefile(L, getfilebyname(L, FINPUT)))
       current = stdin;
     else
       current = NULL;  /* to signal error */
   }
-  else if (lua_tag(f) == gettag())  /* deprecated option */
-    current = lua_getuserdata(f);
+  else if (lua_tag(L, f) == gettag(L))  /* deprecated option */
+    current = lua_getuserdata(L, f);
   else {
-    const char *s = luaL_check_string(FIRSTARG);
+    const char *s = luaL_check_string(L, FIRSTARG);
     current = (*s == '|') ? popen(s+1, "r") : fopen(s, "r");
   }
-  setreturn(current, FINPUT);
+  setreturn(L, current, FINPUT);
 }
 
 
-static void io_writeto (void) {
+static void io_writeto (lua_State *L) {
   FILE *current;
-  lua_Object f = lua_getparam(FIRSTARG);
+  lua_Object f = lua_getparam(L, FIRSTARG);
   if (f == LUA_NOOBJECT) {
-    if (closefile(getfilebyname(FOUTPUT)))
+    if (closefile(L, getfilebyname(L, FOUTPUT)))
       current = stdout;
     else
       current = NULL;  /* to signal error */
   }
-  else if (lua_tag(f) == gettag())  /* deprecated option */
-    current = lua_getuserdata(f);
+  else if (lua_tag(L, f) == gettag(L))  /* deprecated option */
+    current = lua_getuserdata(L, f);
   else {
-    const char *s = luaL_check_string(FIRSTARG);
+    const char *s = luaL_check_string(L, FIRSTARG);
     current = (*s == '|') ? popen(s+1,"w") : fopen(s, "w");
   }
-  setreturn(current, FOUTPUT);
+  setreturn(L, current, FOUTPUT);
 }
 
 
-static void io_appendto (void) {
-  FILE *current = fopen(luaL_check_string(FIRSTARG), "a");
-  setreturn(current, FOUTPUT);
+static void io_appendto (lua_State *L) {
+  FILE *current = fopen(luaL_check_string(L, FIRSTARG), "a");
+  setreturn(L, current, FOUTPUT);
 }
 
 
@@ -232,7 +234,7 @@ static void io_appendto (void) {
 #define NEED_OTHER (EOF-1)  /* just some flag different from EOF */
 
 
-static int read_pattern (FILE *f, const char *p) {
+static int read_pattern (lua_State *L, FILE *f, const char *p) {
   int inskip = 0;  /* {skip} level */
   int c = NEED_OTHER;
   while (*p != '\0') {
@@ -242,17 +244,17 @@ static int read_pattern (FILE *f, const char *p) {
         p++;
         continue;
       case '}':
-        if (!inskip) lua_error("unbalanced braces in read pattern");
+        if (!inskip) lua_error(L, "unbalanced braces in read pattern");
         inskip--;
         p++;
         continue;
       default: {
-        const char *ep = luaI_classend(p);  /* get what is next */
+        const char *ep = luaI_classend(L, p);  /* get what is next */
         int m;  /* match result */
         if (c == NEED_OTHER) c = getc(f);
         m = (c==EOF) ? 0 : luaI_singlematch(c, p, ep);
         if (m) {
-          if (!inskip) luaL_addchar(c);
+          if (!inskip) luaL_addchar(L, c);
           c = NEED_OTHER;
         }
         switch (*ep) {
@@ -263,7 +265,7 @@ static int read_pattern (FILE *f, const char *p) {
             while (m) {  /* reads the same item until it fails */
               c = getc(f);
               m = (c==EOF) ? 0 : luaI_singlematch(c, p, ep);
-              if (m && !inskip) luaL_addchar(c);
+              if (m && !inskip) luaL_addchar(L, c);
             }
             /* go through to continue reading the pattern */
           case '?':  /* optional */
@@ -282,26 +284,26 @@ static int read_pattern (FILE *f, const char *p) {
 
 #else
 
-#define read_pattern(f,p)   (lua_error("read patterns are deprecated"), 0)
+#define read_pattern(L, f,p)   (lua_error(L, "read patterns are deprecated"), 0)
 
 #endif
 
 
-static int read_number (FILE *f) {
+static int read_number (lua_State *L, FILE *f) {
   double d;
   if (fscanf(f, "%lf", &d) == 1) {
-    lua_pushnumber(d);
+    lua_pushnumber(L, d);
     return 1;
   }
   else return 0;  /* read fails */
 }
 
 
-static void read_word (FILE *f) {
+static void read_word (lua_State *L, FILE *f) {
   int c;
   do { c = fgetc(f); } while isspace(c);  /* skip spaces */
   while (c != EOF && !isspace(c)) {
-    luaL_addchar(c);
+    luaL_addchar(L, c);
     c = fgetc(f);
   }
   ungetc(c, f);
@@ -311,127 +313,127 @@ static void read_word (FILE *f) {
 #define HUNK_LINE	256
 #define HUNK_FILE	BUFSIZ
 
-static int read_line (FILE *f) {
+static int read_line (lua_State *L, FILE *f) {
   int n;
   char *b;
   do {
-    b = luaL_openspace(HUNK_LINE);
+    b = luaL_openspace(L, HUNK_LINE);
     if (!fgets(b, HUNK_LINE, f)) return 0;  /* read fails */
     n = strlen(b);
-    luaL_addsize(n); 
+    luaL_addsize(L, n); 
   } while (b[n-1] != '\n');
-  luaL_addsize(-1);  /* remove '\n' */
+  luaL_addsize(L, -1);  /* remove '\n' */
   return 1;
 }
 
 
-static void read_file (FILE *f) {
+static void read_file (lua_State *L, FILE *f) {
   int n;
   do {
-    char *b = luaL_openspace(HUNK_FILE);
+    char *b = luaL_openspace(L, HUNK_FILE);
     n = fread(b, sizeof(char), HUNK_FILE, f);
-    luaL_addsize(n);
+    luaL_addsize(L, n);
   } while (n==HUNK_FILE);
 }
 
 
-static int read_chars (FILE *f, int n) {
-  char *b = luaL_openspace(n);
+static int read_chars (lua_State *L, FILE *f, int n) {
+  char *b = luaL_openspace(L, n);
   int n1 = fread(b, sizeof(char), n, f);
-  luaL_addsize(n1);
+  luaL_addsize(L, n1);
   return (n == n1);
 }
 
 
-static void io_read (void) {
+static void io_read (lua_State *L) {
   int arg = FIRSTARG;
-  FILE *f = getfileparam(FINPUT, &arg);
-  lua_Object op = lua_getparam(arg);
+  FILE *f = getfileparam(L, FINPUT, &arg);
+  lua_Object op = lua_getparam(L, arg);
   do {  /* repeat for each part */
     long l;
     int success;
-    luaL_resetbuffer();
-    if (lua_isnumber(op))
-      success = read_chars(f, (int)lua_getnumber(op));
+    luaL_resetbuffer(L);
+    if (lua_isnumber(L, op))
+      success = read_chars(L, f, (int)lua_getnumber(L, op));
     else {
-      const char *p = luaL_opt_string(arg, "*l");
+      const char *p = luaL_opt_string(L, arg, "*l");
       if (p[0] != '*')
-        success = read_pattern(f, p);  /* deprecated! */
+        success = read_pattern(L, f, p);  /* deprecated! */
       else {
         switch (p[1]) {
           case 'n':  /* number */
-            if (!read_number(f)) return;  /* read fails */
+            if (!read_number(L, f)) return;  /* read fails */
             continue;  /* number is already pushed; avoid the "pushstring" */
           case 'l':  /* line */
-            success = read_line(f);
+            success = read_line(L, f);
             break;
           case 'a':  /* file */
-            read_file(f);
+            read_file(L, f);
             success = 1; /* always success */
             break;
           case 'w':  /* word */
-            read_word(f);
+            read_word(L, f);
             success = 0;  /* must read something to succeed */
             break;
           default:
-            luaL_argerror(arg, "invalid format");
+            luaL_argerror(L, arg, "invalid format");
             success = 0;  /* to avoid warnings */
         }
       }
     }
-    l = luaL_getsize();
+    l = luaL_getsize(L);
     if (!success && l==0) return;  /* read fails */
-    lua_pushlstring(luaL_buffer(), l);
-  } while ((op = lua_getparam(++arg)) != LUA_NOOBJECT);
+    lua_pushlstring(L, luaL_buffer(L), l);
+  } while ((op = lua_getparam(L, ++arg)) != LUA_NOOBJECT);
 }
 
 /* }====================================================== */
 
 
-static void io_write (void) {
+static void io_write (lua_State *L) {
   int arg = FIRSTARG;
-  FILE *f = getfileparam(FOUTPUT, &arg);
+  FILE *f = getfileparam(L, FOUTPUT, &arg);
   int status = 1;
   lua_Object o;
-  while ((o = lua_getparam(arg++)) != LUA_NOOBJECT) {
-    switch (lua_type(o)[2]) {
+  while ((o = lua_getparam(L, arg++)) != LUA_NOOBJECT) {
+    switch (lua_type(L, o)[2]) {
       case 'r': {  /* stRing? */
-        long l = lua_strlen(o);
+        long l = lua_strlen(L, o);
         status = status &&
-                 ((long)fwrite(lua_getstring(o), sizeof(char), l, f) == l);
+                 ((long)fwrite(lua_getstring(L, o), sizeof(char), l, f) == l);
         break;
       }
       case 'm': /* nuMber? */  /* LUA_NUMBER */
         /* optimization: could be done exactly as for strings */
-        status = status && fprintf(f, "%.16g", lua_getnumber(o)) > 0;
+        status = status && fprintf(f, "%.16g", lua_getnumber(L, o)) > 0;
         break;
-      default: luaL_argerror(arg-1, "string expected");
+      default: luaL_argerror(L, arg-1, "string expected");
     }
   }
-  pushresult(status);
+  pushresult(L, status);
 }
 
 
-static void io_seek (void) {
+static void io_seek (lua_State *L) {
   static const int mode[] = {SEEK_SET, SEEK_CUR, SEEK_END};
   static const char *const modenames[] = {"set", "cur", "end", NULL};
-  FILE *f = getnonullfile(FIRSTARG);
-  int op = luaL_findstring(luaL_opt_string(FIRSTARG+1, "cur"), modenames);
-  long offset = luaL_opt_long(FIRSTARG+2, 0);
-  luaL_arg_check(op != -1, FIRSTARG+1, "invalid mode");
+  FILE *f = getnonullfile(L, FIRSTARG);
+  int op = luaL_findstring(luaL_opt_string(L, FIRSTARG+1, "cur"), modenames);
+  long offset = luaL_opt_long(L, FIRSTARG+2, 0);
+  luaL_arg_check(L, op != -1, FIRSTARG+1, "invalid mode");
   op = fseek(f, offset, mode[op]);
   if (op)
-    pushresult(0);  /* error */
+    pushresult(L, 0);  /* error */
   else
-    lua_pushnumber(ftell(f));
+    lua_pushnumber(L, ftell(f));
 }
 
 
-static void io_flush (void) {
-  FILE *f = getfile(FIRSTARG);
-  luaL_arg_check(f || lua_getparam(FIRSTARG) == LUA_NOOBJECT, FIRSTARG,
+static void io_flush (lua_State *L) {
+  FILE *f = getfile(L, FIRSTARG);
+  luaL_arg_check(L, f || lua_getparam(L, FIRSTARG) == LUA_NOOBJECT, FIRSTARG,
                  "invalid file handle");
-  pushresult(fflush(f) == 0);
+  pushresult(L, fflush(f) == 0);
 }
 
 /* }====================================================== */
@@ -443,102 +445,102 @@ static void io_flush (void) {
 ** =======================================================
 */
 
-static void io_execute (void) {
-  lua_pushnumber(system(luaL_check_string(1)));
+static void io_execute (lua_State *L) {
+  lua_pushnumber(L, system(luaL_check_string(L, 1)));
 }
 
 
-static void io_remove  (void) {
-  pushresult(remove(luaL_check_string(1)) == 0);
+static void io_remove (lua_State *L) {
+  pushresult(L, remove(luaL_check_string(L, 1)) == 0);
 }
 
 
-static void io_rename (void) {
-  pushresult(rename(luaL_check_string(1),
-                    luaL_check_string(2)) == 0);
+static void io_rename (lua_State *L) {
+  pushresult(L, rename(luaL_check_string(L, 1),
+                    luaL_check_string(L, 2)) == 0);
 }
 
 
-static void io_tmpname (void) {
-  lua_pushstring(tmpnam(NULL));
+static void io_tmpname (lua_State *L) {
+  lua_pushstring(L, tmpnam(NULL));
 }
 
 
 
-static void io_getenv (void) {
-  lua_pushstring(getenv(luaL_check_string(1)));  /* if NULL push nil */
+static void io_getenv (lua_State *L) {
+  lua_pushstring(L, getenv(luaL_check_string(L, 1)));  /* if NULL push nil */
 }
 
 
-static void io_clock (void) {
-  lua_pushnumber(((double)clock())/CLOCKS_PER_SEC);
+static void io_clock (lua_State *L) {
+  lua_pushnumber(L, ((double)clock())/CLOCKS_PER_SEC);
 }
 
 
-static void io_date (void) {
+static void io_date (lua_State *L) {
   char b[256];
-  const char *s = luaL_opt_string(1, "%c");
+  const char *s = luaL_opt_string(L, 1, "%c");
   struct tm *tm;
   time_t t;
   time(&t); tm = localtime(&t);
   if (strftime(b,sizeof(b),s,tm))
-    lua_pushstring(b);
+    lua_pushstring(L, b);
   else
-    lua_error("invalid `date' format");
+    lua_error(L, "invalid `date' format");
 }
 
 
-static void setloc (void) {
+static void setloc (lua_State *L) {
   static const int cat[] = {LC_ALL, LC_COLLATE, LC_CTYPE, LC_MONETARY,
                       LC_NUMERIC, LC_TIME};
   static const char *const catnames[] = {"all", "collate", "ctype", "monetary",
      "numeric", "time", NULL};
-  int op = luaL_findstring(luaL_opt_string(2, "all"), catnames);
-  luaL_arg_check(op != -1, 2, "invalid option");
-  lua_pushstring(setlocale(cat[op], luaL_check_string(1)));
+  int op = luaL_findstring(luaL_opt_string(L, 2, "all"), catnames);
+  luaL_arg_check(L, op != -1, 2, "invalid option");
+  lua_pushstring(L, setlocale(cat[op], luaL_check_string(L, 1)));
 }
 
 
-static void io_exit (void) {
-  exit(luaL_opt_int(1, EXIT_SUCCESS));
+static void io_exit (lua_State *L) {
+  exit(luaL_opt_int(L, 1, EXIT_SUCCESS));
 }
 
 /* }====================================================== */
 
 
 
-static void io_debug (void) {
+static void io_debug (lua_State *L) {
   for (;;) {
     char buffer[250];
     fprintf(stderr, "lua_debug> ");
     if (fgets(buffer, sizeof(buffer), stdin) == 0 ||
         strcmp(buffer, "cont\n") == 0)
       return;
-    lua_dostring(buffer);
+    lua_dostring(L, buffer);
   }
 }
 
 
 
 #define MESSAGESIZE	150
-#define MAXMESSAGE	(MESSAGESIZE*10)
+#define MAXMESSAGE (MESSAGESIZE*10)
 
 
 #define MAXSRC		60
 
 
-static void errorfb (void) {
+static void errorfb (lua_State *L) {
   char buff[MAXMESSAGE];
   int level = 1;  /* skip level 0 (it's this function) */
   lua_Object func;
-  sprintf(buff, "lua error: %.200s\n", lua_getstring(lua_getparam(1)));
-  while ((func = lua_stackedfunction(level++)) != LUA_NOOBJECT) {
+  sprintf(buff, "lua error: %.200s\n", lua_getstring(L, lua_getparam(L, 1)));
+  while ((func = lua_stackedfunction(L, level++)) != LUA_NOOBJECT) {
     const char *name;
     int currentline;
     const char *chunkname;
     char buffchunk[MAXSRC];
     int linedefined;
-    lua_funcinfo(func, &chunkname, &linedefined);
+    lua_funcinfo(L, func, &chunkname, &linedefined);
     luaL_chunkid(buffchunk, chunkname, sizeof(buffchunk));
     if (level == 2) strcat(buff, "Active Stack:\n");
     strcat(buff, "  ");
@@ -546,7 +548,7 @@ static void errorfb (void) {
       strcat(buff, "...\n");
       break;  /* buffer is full */
     }
-    switch (*lua_getobjname(func, &name)) {
+    switch (*lua_getobjname(L, func, &name)) {
       case 'g':
         sprintf(buff+strlen(buff), "function `%.50s'", name);
         break;
@@ -564,16 +566,16 @@ static void errorfb (void) {
         chunkname = NULL;
       }
     }
-    if ((currentline = lua_currentline(func)) > 0)
+    if ((currentline = lua_currentline(L, func)) > 0)
       sprintf(buff+strlen(buff), " at line %d", currentline);
     if (chunkname)
       sprintf(buff+strlen(buff), " [%.70s]", buffchunk);
     strcat(buff, "\n");
   }
-  func = lua_rawgetglobal("_ALERT");
-  if (lua_isfunction(func)) {  /* avoid error loop if _ALERT is not defined */
-    lua_pushstring(buff);
-    lua_callfunction(func);
+  func = lua_rawgetglobal(L, "_ALERT");
+  if (lua_isfunction(L, func)) {  /* avoid error loop if _ALERT is not defined */
+    lua_pushstring(L, buff);
+    lua_callfunction(L, func);
   }
 }
 
@@ -607,31 +609,31 @@ static const struct luaL_reg iolibtag[] = {
 };
 
 
-static void openwithtags (void) {
+static void openwithtags (lua_State *L) {
   unsigned int i;
-  int iotag = lua_newtag();
-  lua_newtag();  /* alloc CLOSEDTAG: assume that CLOSEDTAG = iotag-1 */
+  int iotag = lua_newtag(L);
+  lua_newtag(L);  /* alloc CLOSEDTAG: assume that CLOSEDTAG = iotag-1 */
   for (i=0; i<sizeof(iolibtag)/sizeof(iolibtag[0]); i++) {
     /* put iotag as upvalue for these functions */
-    lua_pushnumber(iotag);
-    lua_pushcclosure(iolibtag[i].func, 1);
-    lua_setglobal(iolibtag[i].name);
+    lua_pushnumber(L, iotag);
+    lua_pushcclosure(L, iolibtag[i].func, 1);
+    lua_setglobal(L, iolibtag[i].name);
   }
   /* predefined file handles */
-  setfile(stdin, FINPUT, iotag);
-  setfile(stdout, FOUTPUT, iotag);
-  setfile(stdin, "_STDIN", iotag);
-  setfile(stdout, "_STDOUT", iotag);
-  setfile(stderr, "_STDERR", iotag);
+  setfile(L, stdin, FINPUT, iotag);
+  setfile(L, stdout, FOUTPUT, iotag);
+  setfile(L, stdin, "_STDIN", iotag);
+  setfile(L, stdout, "_STDOUT", iotag);
+  setfile(L, stderr, "_STDERR", iotag);
   /* close file when collected */
-  lua_pushnumber(iotag);
-  lua_pushcclosure(gc_close, 1); 
-  lua_settagmethod(iotag, "gc");
+  lua_pushnumber(L, iotag);
+  lua_pushcclosure(L, gc_close, 1); 
+  lua_settagmethod(L, iotag, "gc");
 }
 
-void lua_iolibopen (void) {
+void lua_iolibopen (lua_State *L) {
   /* register lib functions */
-  luaL_openlib(iolib, (sizeof(iolib)/sizeof(iolib[0])));
-  openwithtags();
+  luaL_openlib(L, iolib, (sizeof(iolib)/sizeof(iolib[0])));
+  openwithtags(L);
 }
 

+ 77 - 74
llex.c

@@ -1,5 +1,5 @@
 /*
-** $Id: llex.c,v 1.42 1999/10/19 13:33:22 roberto Exp roberto $
+** $Id: llex.c,v 1.43 1999/11/09 17:59:35 roberto Exp roberto $
 ** Lexical Analyzer
 ** See Copyright Notice in lua.h
 */
@@ -8,6 +8,8 @@
 #include <ctype.h>
 #include <string.h>
 
+#define LUA_REENTRANT
+
 #include "lauxlib.h"
 #include "llex.h"
 #include "lmem.h"
@@ -23,8 +25,8 @@
 #define next(LS) (LS->current = zgetc(LS->lex_z))
 
 
-#define save(c)	luaL_addchar(c)
-#define save_and_next(LS)  (save(LS->current), next(LS))
+#define save(L, c)	luaL_addchar(L, c)
+#define save_and_next(L, LS)  (save(L, LS->current), next(LS))
 
 
 /* ORDER RESERVED */
@@ -33,10 +35,10 @@ static const char *const reserved [] = {"and", "do", "else", "elseif", "end",
     "until", "while"};
 
 
-void luaX_init (void) {
+void luaX_init (lua_State *L) {
   unsigned int i;
   for (i=0; i<(sizeof(reserved)/sizeof(reserved[0])); i++) {
-    TaggedString *ts = luaS_new(reserved[i]);
+    TaggedString *ts = luaS_new(L, reserved[i]);
     ts->marked = (unsigned char)(RESERVEDMARK+i);  /* reserved word */
   }
 }
@@ -49,14 +51,14 @@ void luaX_syntaxerror (LexState *ls, const char *s, const char *token) {
   luaL_chunkid(buff, zname(ls->lex_z), sizeof(buff));
   if (token[0] == '\0')
     token = "<eof>";
-  luaL_verror("%.100s;\n  last token read: `%.50s' at line %d in %.80s",
+  luaL_verror(ls->L, "%.100s;\n  last token read: `%.50s' at line %d in %.80s",
               s, token, ls->linenumber, buff);
 }
 
 
 void luaX_error (LexState *ls, const char *s) {
-  save('\0');
-  luaX_syntaxerror(ls, s, luaL_buffer());
+  save(ls->L, '\0');
+  luaX_syntaxerror(ls, s, luaL_buffer(ls->L));
 }
 
 
@@ -86,8 +88,8 @@ static void firstline (LexState *LS)
 }
 
 
-void luaX_setinput (LexState *LS, ZIO *z)
-{
+void luaX_setinput (lua_State *L, LexState *LS, ZIO *z) {
+  LS->L = L;
   LS->current = '\n';
   LS->linenumber = 0;
   LS->iflevel = 0;
@@ -96,7 +98,7 @@ void luaX_setinput (LexState *LS, ZIO *z)
   LS->lex_z = z;
   LS->fs = NULL;
   firstline(LS);
-  luaL_resetbuffer();
+  luaL_resetbuffer(L);
 }
 
 
@@ -117,12 +119,12 @@ static void skipspace (LexState *LS) {
 }
 
 
-static int checkcond (LexState *LS, const char *buff) {
+static int checkcond (lua_State *L, LexState *LS, const char *buff) {
   static const char *const opts[] = {"nil", "1", NULL};
   int i = luaL_findstring(buff, opts);
   if (i >= 0) return i;
   else if (isalpha((unsigned char)buff[0]) || buff[0] == '_')
-    return luaS_globaldefined(buff);
+    return luaS_globaldefined(L, buff);
   else {
     luaX_syntaxerror(LS, "invalid $if condition", buff);
     return 0;  /* to avoid warnings */
@@ -145,13 +147,13 @@ static void readname (LexState *LS, char *buff) {
 }
 
 
-static void inclinenumber (LexState *LS);
+static void inclinenumber (lua_State *L, LexState *LS);
 
 
-static void ifskip (LexState *LS) {
+static void ifskip (lua_State *L, LexState *LS) {
   while (LS->ifstate[LS->iflevel].skip) {
     if (LS->current == '\n')
-      inclinenumber(LS);
+      inclinenumber(L, LS);
     else if (LS->current == EOZ)
       luaX_error(LS, "input ends inside a $if");
     else next(LS);
@@ -159,7 +161,7 @@ static void ifskip (LexState *LS) {
 }
 
 
-static void inclinenumber (LexState *LS) {
+static void inclinenumber (lua_State *L, LexState *LS) {
   static const char *const pragmas [] =
     {"debug", "nodebug", "endinput", "end", "ifnot", "if", "else", NULL};
   next(LS);  /* skip '\n' */
@@ -196,7 +198,7 @@ static void inclinenumber (LexState *LS) {
         readname(LS, buff);
         LS->iflevel++;
         LS->ifstate[LS->iflevel].elsepart = 0;
-        LS->ifstate[LS->iflevel].condition = checkcond(LS, buff) ? !ifnot : ifnot;
+        LS->ifstate[LS->iflevel].condition = checkcond(L, LS, buff) ? !ifnot : ifnot;
         LS->ifstate[LS->iflevel].skip = skip || !LS->ifstate[LS->iflevel].condition;
         break;
       case 6:  /* else */
@@ -211,10 +213,10 @@ static void inclinenumber (LexState *LS) {
     }
     skipspace(LS);
     if (LS->current == '\n')  /* pragma must end with a '\n' ... */
-      inclinenumber(LS);
+      inclinenumber(L, LS);
     else if (LS->current != EOZ)  /* or eof */
       luaX_syntaxerror(LS, "invalid pragma format", buff);
-    ifskip(LS);
+    ifskip(L, LS);
   }
 }
 
@@ -228,7 +230,7 @@ static void inclinenumber (LexState *LS) {
 
 
 
-static int read_long_string (LexState *LS) {
+static int read_long_string (lua_State *L, LexState *LS) {
   int cont = 0;
   for (;;) {
     switch (LS->current) {
@@ -236,37 +238,38 @@ static int read_long_string (LexState *LS) {
         luaX_error(LS, "unfinished long string");
         return EOS;  /* to avoid warnings */
       case '[':
-        save_and_next(LS);
+        save_and_next(L, LS);
         if (LS->current == '[') {
           cont++;
-          save_and_next(LS);
+          save_and_next(L, LS);
         }
         continue;
       case ']':
-        save_and_next(LS);
+        save_and_next(L, LS);
         if (LS->current == ']') {
           if (cont == 0) goto endloop;
           cont--;
-          save_and_next(LS);
+          save_and_next(L, LS);
         }
         continue;
       case '\n':
-        save('\n');
-        inclinenumber(LS);
+        save(L, '\n');
+        inclinenumber(L, LS);
         continue;
       default:
-        save_and_next(LS);
+        save_and_next(L, LS);
     }
   } endloop:
-  save_and_next(LS);  /* skip the second ']' */
-  LS->seminfo.ts = luaS_newlstr(L->Mbuffer+(L->Mbuffbase+2),
+  save_and_next(L, LS);  /* skip the second ']' */
+  LS->seminfo.ts = luaS_newlstr(L, L->Mbuffer+(L->Mbuffbase+2),
                           L->Mbuffnext-L->Mbuffbase-4);
   return STRING;
 }
 
 
 int luaX_lex (LexState *LS) {
-  luaL_resetbuffer();
+  lua_State *L = LS->L;
+  luaL_resetbuffer(L);
   for (;;) {
     switch (LS->current) {
 
@@ -275,48 +278,48 @@ int luaX_lex (LexState *LS) {
         continue;
 
       case '\n':
-        inclinenumber(LS);
+        inclinenumber(L, LS);
         continue;
 
       case '-':
-        save_and_next(LS);
+        save_and_next(L, LS);
         if (LS->current != '-') return '-';
         do { next(LS); } while (LS->current != '\n' && LS->current != EOZ);
-        luaL_resetbuffer();
+        luaL_resetbuffer(L);
         continue;
 
       case '[':
-        save_and_next(LS);
+        save_and_next(L, LS);
         if (LS->current != '[') return '[';
         else {
-          save_and_next(LS);  /* pass the second '[' */
-          return read_long_string(LS);
+          save_and_next(L, LS);  /* pass the second '[' */
+          return read_long_string(L, LS);
         }
 
       case '=':
-        save_and_next(LS);
+        save_and_next(L, LS);
         if (LS->current != '=') return '=';
-        else { save_and_next(LS); return EQ; }
+        else { save_and_next(L, LS); return EQ; }
 
       case '<':
-        save_and_next(LS);
+        save_and_next(L, LS);
         if (LS->current != '=') return '<';
-        else { save_and_next(LS); return LE; }
+        else { save_and_next(L, LS); return LE; }
 
       case '>':
-        save_and_next(LS);
+        save_and_next(L, LS);
         if (LS->current != '=') return '>';
-        else { save_and_next(LS); return GE; }
+        else { save_and_next(L, LS); return GE; }
 
       case '~':
-        save_and_next(LS);
+        save_and_next(L, LS);
         if (LS->current != '=') return '~';
-        else { save_and_next(LS); return NE; }
+        else { save_and_next(L, LS); return NE; }
 
       case '"':
       case '\'': {
         int del = LS->current;
-        save_and_next(LS);
+        save_and_next(L, LS);
         while (LS->current != del) {
           switch (LS->current) {
             case EOZ:
@@ -326,14 +329,14 @@ int luaX_lex (LexState *LS) {
             case '\\':
               next(LS);  /* do not save the '\' */
               switch (LS->current) {
-                case 'a': save('\a'); next(LS); break;
-                case 'b': save('\b'); next(LS); break;
-                case 'f': save('\f'); next(LS); break;
-                case 'n': save('\n'); next(LS); break;
-                case 'r': save('\r'); next(LS); break;
-                case 't': save('\t'); next(LS); break;
-                case 'v': save('\v'); next(LS); break;
-                case '\n': save('\n'); inclinenumber(LS); break;
+                case 'a': save(L, '\a'); next(LS); break;
+                case 'b': save(L, '\b'); next(LS); break;
+                case 'f': save(L, '\f'); next(LS); break;
+                case 'n': save(L, '\n'); next(LS); break;
+                case 'r': save(L, '\r'); next(LS); break;
+                case 't': save(L, '\t'); next(LS); break;
+                case 'v': save(L, '\v'); next(LS); break;
+                case '\n': save(L, '\n'); inclinenumber(L, LS); break;
                 default : {
                   if (isdigit(LS->current)) {
                     int c = 0;
@@ -344,10 +347,10 @@ int luaX_lex (LexState *LS) {
                     } while (++i<3 && isdigit(LS->current));
                     if (c != (unsigned char)c)
                       luaX_error(LS, "escape sequence too large");
-                    save(c);
+                    save(L, c);
                   }
                   else {  /* handles \, ", ', and ? */
-                    save(LS->current);
+                    save(L, LS->current);
                     next(LS);
                   }
                   break;
@@ -355,23 +358,23 @@ int luaX_lex (LexState *LS) {
               }
               break;
             default:
-              save_and_next(LS);
+              save_and_next(L, LS);
           }
         }
-        save_and_next(LS);  /* skip delimiter */
-        LS->seminfo.ts = luaS_newlstr(L->Mbuffer+(L->Mbuffbase+1),
+        save_and_next(L, LS);  /* skip delimiter */
+        LS->seminfo.ts = luaS_newlstr(L, L->Mbuffer+(L->Mbuffbase+1),
                                 L->Mbuffnext-L->Mbuffbase-2);
         return STRING;
       }
 
       case '.':
-        save_and_next(LS);
+        save_and_next(L, LS);
         if (LS->current == '.')
         {
-          save_and_next(LS);
+          save_and_next(L, LS);
           if (LS->current == '.')
           {
-            save_and_next(LS);
+            save_and_next(L, LS);
             return DOTS;   /* ... */
           }
           else return CONC;   /* .. */
@@ -382,26 +385,26 @@ int luaX_lex (LexState *LS) {
       case '0': case '1': case '2': case '3': case '4':
       case '5': case '6': case '7': case '8': case '9':
         do {
-          save_and_next(LS);
+          save_and_next(L, LS);
         } while (isdigit(LS->current));
         if (LS->current == '.') {
-          save_and_next(LS);
+          save_and_next(L, LS);
           if (LS->current == '.') {
-            save('.');
+            save(L, '.');
             luaX_error(LS, 
               "ambiguous syntax (decimal point x string concatenation)");
           }
         }
       fraction:  /* LUA_NUMBER */
         while (isdigit(LS->current))
-          save_and_next(LS);
+          save_and_next(L, LS);
         if (toupper(LS->current) == 'E') {
-          save_and_next(LS);  /* read 'E' */
-          save_and_next(LS);  /* read '+', '-' or first digit */
+          save_and_next(L, LS);  /* read 'E' */
+          save_and_next(L, LS);  /* read '+', '-' or first digit */
           while (isdigit(LS->current))
-            save_and_next(LS);
+            save_and_next(L, LS);
         }
-        save('\0');
+        save(L, '\0');
         if (!luaO_str2d(L->Mbuffer+L->Mbuffbase, &LS->seminfo.r))
           luaX_error(LS, "invalid numeric format");
         return NUMBER;
@@ -416,16 +419,16 @@ int luaX_lex (LexState *LS) {
           int c = LS->current;
           if (iscntrl(c))
             luaX_invalidchar(LS, c);
-          save_and_next(LS);
+          save_and_next(L, LS);
           return c;
         }
         else {  /* identifier or reserved word */
           TaggedString *ts;
           do {
-            save_and_next(LS);
+            save_and_next(L, LS);
           } while (isalnum(LS->current) || LS->current == '_');
-          save('\0');
-          ts = luaS_new(L->Mbuffer+L->Mbuffbase);
+          save(L, '\0');
+          ts = luaS_new(L, L->Mbuffer+L->Mbuffbase);
           if (ts->marked >= RESERVEDMARK)  /* reserved word? */
             return ts->marked-RESERVEDMARK+FIRST_RESERVED;
           LS->seminfo.ts = ts;

+ 4 - 3
llex.h

@@ -1,5 +1,5 @@
 /*
-** $Id: llex.h,v 1.13 1999/07/22 19:29:42 roberto Exp roberto $
+** $Id: llex.h,v 1.14 1999/08/16 20:52:00 roberto Exp roberto $
 ** Lexical Analyzer
 ** See Copyright Notice in lua.h
 */
@@ -47,6 +47,7 @@ typedef struct LexState {
   int current;  /* look ahead character */
   int token;  /* look ahead token */
   struct FuncState *fs;  /* 'FuncState' is private for the parser */
+  struct lua_State *L;
   union {
     real r;
     TaggedString *ts;
@@ -58,8 +59,8 @@ typedef struct LexState {
 } LexState;
 
 
-void luaX_init (void);
-void luaX_setinput (LexState *LS, ZIO *z);
+void luaX_init (lua_State *L);
+void luaX_setinput (lua_State *L, LexState *LS, ZIO *z);
 int luaX_lex (LexState *LS);
 void luaX_syntaxerror (LexState *ls, const char *s, const char *token);
 void luaX_error (LexState *ls, const char *s);

+ 73 - 71
lmathlib.c

@@ -1,5 +1,5 @@
 /*
-** $Id: lmathlib.c,v 1.18 1999/08/16 20:52:00 roberto Exp roberto $
+** $Id: lmathlib.c,v 1.19 1999/08/18 14:40:51 roberto Exp roberto $
 ** Lua standard mathematical library
 ** See Copyright Notice in lua.h
 */
@@ -8,14 +8,16 @@
 #include <stdlib.h>
 #include <math.h>
 
+#define LUA_REENTRANT
+
 #include "lauxlib.h"
 #include "lua.h"
 #include "lualib.h"
 
 
 #undef PI
-#define PI	(3.14159265358979323846)
-#define RADIANS_PER_DEGREE	(PI/180.0)
+#define PI (3.14159265358979323846)
+#define RADIANS_PER_DEGREE (PI/180.0)
 
 
 
@@ -32,138 +34,138 @@
 #endif
 
 
-static void math_abs (void) {
-  lua_pushnumber(fabs(luaL_check_number(1)));
+static void math_abs (lua_State *L) {
+  lua_pushnumber(L, fabs(luaL_check_number(L, 1)));
 }
 
-static void math_sin (void) {
-  lua_pushnumber(sin(TORAD(luaL_check_number(1))));
+static void math_sin (lua_State *L) {
+  lua_pushnumber(L, sin(TORAD(luaL_check_number(L, 1))));
 }
 
-static void math_cos (void) {
-  lua_pushnumber(cos(TORAD(luaL_check_number(1))));
+static void math_cos (lua_State *L) {
+  lua_pushnumber(L, cos(TORAD(luaL_check_number(L, 1))));
 }
 
-static void math_tan (void) {
-  lua_pushnumber(tan(TORAD(luaL_check_number(1))));
+static void math_tan (lua_State *L) {
+  lua_pushnumber(L, tan(TORAD(luaL_check_number(L, 1))));
 }
 
-static void math_asin (void) {
-  lua_pushnumber(FROMRAD(asin(luaL_check_number(1))));
+static void math_asin (lua_State *L) {
+  lua_pushnumber(L, FROMRAD(asin(luaL_check_number(L, 1))));
 }
 
-static void math_acos (void) {
-  lua_pushnumber(FROMRAD(acos(luaL_check_number(1))));
+static void math_acos (lua_State *L) {
+  lua_pushnumber(L, FROMRAD(acos(luaL_check_number(L, 1))));
 }
 
-static void math_atan (void) {
-  lua_pushnumber(FROMRAD(atan(luaL_check_number(1))));
+static void math_atan (lua_State *L) {
+  lua_pushnumber(L, FROMRAD(atan(luaL_check_number(L, 1))));
 }
 
-static void math_atan2 (void) {
-  lua_pushnumber(FROMRAD(atan2(luaL_check_number(1), luaL_check_number(2))));
+static void math_atan2 (lua_State *L) {
+  lua_pushnumber(L, FROMRAD(atan2(luaL_check_number(L, 1), luaL_check_number(L, 2))));
 }
 
-static void math_ceil (void) {
-  lua_pushnumber(ceil(luaL_check_number(1)));
+static void math_ceil (lua_State *L) {
+  lua_pushnumber(L, ceil(luaL_check_number(L, 1)));
 }
 
-static void math_floor (void) {
-  lua_pushnumber(floor(luaL_check_number(1)));
+static void math_floor (lua_State *L) {
+  lua_pushnumber(L, floor(luaL_check_number(L, 1)));
 }
 
-static void math_mod (void) {
-  lua_pushnumber(fmod(luaL_check_number(1), luaL_check_number(2)));
+static void math_mod (lua_State *L) {
+  lua_pushnumber(L, fmod(luaL_check_number(L, 1), luaL_check_number(L, 2)));
 }
 
-static void math_sqrt (void) {
-  lua_pushnumber(sqrt(luaL_check_number(1)));
+static void math_sqrt (lua_State *L) {
+  lua_pushnumber(L, sqrt(luaL_check_number(L, 1)));
 }
 
-static void math_pow (void) {
-  lua_pushnumber(pow(luaL_check_number(1), luaL_check_number(2)));
+static void math_pow (lua_State *L) {
+  lua_pushnumber(L, pow(luaL_check_number(L, 1), luaL_check_number(L, 2)));
 }
 
-static void math_log (void) {
-  lua_pushnumber(log(luaL_check_number(1)));
+static void math_log (lua_State *L) {
+  lua_pushnumber(L, log(luaL_check_number(L, 1)));
 }
 
-static void math_log10 (void) {
-  lua_pushnumber(log10(luaL_check_number(1)));
+static void math_log10 (lua_State *L) {
+  lua_pushnumber(L, log10(luaL_check_number(L, 1)));
 }
 
-static void math_exp (void) {
-  lua_pushnumber(exp(luaL_check_number(1)));
+static void math_exp (lua_State *L) {
+  lua_pushnumber(L, exp(luaL_check_number(L, 1)));
 }
 
-static void math_deg (void) {
-  lua_pushnumber(luaL_check_number(1)/RADIANS_PER_DEGREE);
+static void math_deg (lua_State *L) {
+  lua_pushnumber(L, luaL_check_number(L, 1)/RADIANS_PER_DEGREE);
 }
 
-static void math_rad (void) {
-  lua_pushnumber(luaL_check_number(1)*RADIANS_PER_DEGREE);
+static void math_rad (lua_State *L) {
+  lua_pushnumber(L, luaL_check_number(L, 1)*RADIANS_PER_DEGREE);
 }
 
-static void math_frexp (void) {
+static void math_frexp (lua_State *L) {
   int e;
-  lua_pushnumber(frexp(luaL_check_number(1), &e));
-  lua_pushnumber(e);
+  lua_pushnumber(L, frexp(luaL_check_number(L, 1), &e));
+  lua_pushnumber(L, e);
 }
 
-static void math_ldexp (void) {
-  lua_pushnumber(ldexp(luaL_check_number(1), luaL_check_int(2)));
+static void math_ldexp (lua_State *L) {
+  lua_pushnumber(L, ldexp(luaL_check_number(L, 1), luaL_check_int(L, 2)));
 }
 
 
 
-static void math_min (void) {
+static void math_min (lua_State *L) {
   int i = 1;
-  double dmin = luaL_check_number(i);
-  while (lua_getparam(++i) != LUA_NOOBJECT) {
-    double d = luaL_check_number(i);
+  double dmin = luaL_check_number(L, i);
+  while (lua_getparam(L, ++i) != LUA_NOOBJECT) {
+    double d = luaL_check_number(L, i);
     if (d < dmin)
       dmin = d;
   }
-  lua_pushnumber(dmin);
+  lua_pushnumber(L, dmin);
 }
 
 
-static void math_max (void) {
+static void math_max (lua_State *L) {
   int i = 1;
-  double dmax = luaL_check_number(i);
-  while (lua_getparam(++i) != LUA_NOOBJECT) {
-    double d = luaL_check_number(i);
+  double dmax = luaL_check_number(L, i);
+  while (lua_getparam(L, ++i) != LUA_NOOBJECT) {
+    double d = luaL_check_number(L, i);
     if (d > dmax)
       dmax = d;
   }
-  lua_pushnumber(dmax);
+  lua_pushnumber(L, dmax);
 }
 
 
-static void math_random (void) {
+static void math_random (lua_State *L) {
   /* the '%' avoids the (rare) case of r==1, and is needed also because on
      some systems (SunOS!) "rand()" may return a value bigger than RAND_MAX */
   double r = (double)(rand()%RAND_MAX) / (double)RAND_MAX;
-  if (lua_getparam(1) == LUA_NOOBJECT)  /* no arguments? */
-    lua_pushnumber(r);  /* real between 0 & 1 */
+  if (lua_getparam(L, 1) == LUA_NOOBJECT)  /* no arguments? */
+    lua_pushnumber(L, r);  /* real between 0 & 1 */
   else {
     int l, u;  /* lower & upper limits */
-    if (lua_getparam(2) == LUA_NOOBJECT) {  /* only one argument? */
+    if (lua_getparam(L, 2) == LUA_NOOBJECT) {  /* only one argument? */
       l = 1;
-      u = luaL_check_int(1);
+      u = luaL_check_int(L, 1);
     }
     else {  /* two arguments */
-      l = luaL_check_int(1);
-      u = luaL_check_int(2);
+      l = luaL_check_int(L, 1);
+      u = luaL_check_int(L, 2);
     }
-    luaL_arg_check(l<=u, 1, "interval is empty");
-    lua_pushnumber((int)(r*(u-l+1))+l);  /* integer between l & u */
+    luaL_arg_check(L, l<=u, 1, "interval is empty");
+    lua_pushnumber(L, (int)(r*(u-l+1))+l);  /* integer between l & u */
   }
 }
 
 
-static void math_randomseed (void) {
-  srand(luaL_check_int(1));
+static void math_randomseed (lua_State *L) {
+  srand(luaL_check_int(L, 1));
 }
 
 
@@ -196,11 +198,11 @@ static const struct luaL_reg mathlib[] = {
 /*
 ** Open math library
 */
-void lua_mathlibopen (void) {
-  luaL_openlib(mathlib, (sizeof(mathlib)/sizeof(mathlib[0])));
-  lua_pushcfunction(math_pow);
-  lua_pushnumber(0);  /* to get its tag */
-  lua_settagmethod(lua_tag(lua_pop()), "pow");
-  lua_pushnumber(PI); lua_setglobal("PI");
+void lua_mathlibopen (lua_State *L) {
+  luaL_openlib(L, mathlib, (sizeof(mathlib)/sizeof(mathlib[0])));
+  lua_pushcfunction(L, math_pow);
+  lua_pushnumber(L, 0);  /* to get its tag */
+  lua_settagmethod(L, lua_tag(L, lua_pop(L)), "pow");
+  lua_pushnumber(L, PI); lua_setglobal(L, "PI");
 }
 

+ 13 - 11
lmem.c

@@ -1,5 +1,5 @@
 /*
-** $Id: lmem.c,v 1.18 1999/08/16 20:52:00 roberto Exp roberto $
+** $Id: lmem.c,v 1.19 1999/10/19 13:33:22 roberto Exp roberto $
 ** Interface to Memory Manager
 ** See Copyright Notice in lua.h
 */
@@ -7,6 +7,8 @@
 
 #include <stdlib.h>
 
+#define LUA_REENTRANT
+
 #include "lmem.h"
 #include "lstate.h"
 #include "lua.h"
@@ -34,15 +36,15 @@ static unsigned long power2 (unsigned long n) {
 }
 
 
-void *luaM_growaux (void *block, unsigned long nelems, int inc, int size,
+void *luaM_growaux (lua_State *L, void *block, unsigned long nelems, int inc, int size,
                        const char *errormsg, unsigned long limit) {
   unsigned long newn = nelems+inc;
-  if (newn >= limit) lua_error(errormsg);
+  if (newn >= limit) lua_error(L, errormsg);
   if ((newn ^ nelems) <= nelems ||  /* still the same power of 2 limit? */
        (nelems > 0 && newn < MINSIZE))  /* or block already is MINSIZE? */
       return block;  /* do not need to reallocate */
   else  /* it crossed a power of 2 boundary; grow to next power */
-    return luaM_realloc(block, power2(newn)*size);
+    return luaM_realloc(L, block, power2(newn)*size);
 }
 
 
@@ -51,17 +53,17 @@ void *luaM_growaux (void *block, unsigned long nelems, int inc, int size,
 /*
 ** generic allocation routine.
 */
-void *luaM_realloc (void *block, unsigned long size) {
+void *luaM_realloc (lua_State *L, void *block, unsigned long size) {
   size_t s = (size_t)size;
   if (s != size)
-    lua_error("memory allocation error: block too big");
+    lua_error(L, "memory allocation error: block too big");
   if (size == 0) {
     free(block);  /* block may be NULL, that is OK for free */
     return NULL;
   }
   block = realloc(block, s);
   if (block == NULL)
-    lua_error(memEM);
+    lua_error(L, memEM);
   return block;
 }
 
@@ -90,7 +92,7 @@ static void *checkblock (void *block) {
   unsigned long size = *b;
   int i;
   for (i=0;i<MARKSIZE;i++)
-    LUA_ASSERT(*(((char *)b)+HEADER+size+i) == MARK+i, "corrupted block");
+    LUA_ASSERT(L, *(((char *)b)+HEADER+size+i) == MARK+i, "corrupted block");
   numblocks--;
   totalmem -= size;
   return b;
@@ -106,10 +108,10 @@ static void freeblock (void *block) {
 }
 
 
-void *luaM_realloc (void *block, unsigned long size) {
+void *luaM_realloc (lua_State *L, void *block, unsigned long size) {
   unsigned long realsize = HEADER+size+MARKSIZE;
   if (realsize != (size_t)realsize)
-    lua_error("memory allocation error: block too big");
+    lua_error(L, "memory allocation error: block too big");
   if (size == 0) {
     freeblock(block);
     return NULL;
@@ -124,7 +126,7 @@ void *luaM_realloc (void *block, unsigned long size) {
       freeblock(block);  /* erase (and check) old copy */
     }
     if (newblock == NULL)
-      lua_error(memEM);
+      lua_error(L, memEM);
     totalmem += size;
     numblocks++;
     *(unsigned long *)newblock = size;

+ 12 - 10
lmem.h

@@ -1,5 +1,5 @@
 /*
-** $Id: lmem.h,v 1.8 1999/02/26 15:48:55 roberto Exp roberto $
+** $Id: lmem.h,v 1.9 1999/08/16 20:52:00 roberto Exp roberto $
 ** Interface to Memory Manager
 ** See Copyright Notice in lua.h
 */
@@ -10,6 +10,8 @@
 
 #include <stdlib.h>
 
+#include "lua.h"
+
 /* memory error messages */
 #define codeEM   "code size overflow"
 #define constantEM   "constant table overflow"
@@ -18,17 +20,17 @@
 #define memEM "not enough memory"
 #define arrEM	"internal array bigger than `int' limit"
 
-void *luaM_realloc (void *oldblock, unsigned long size);
-void *luaM_growaux (void *block, unsigned long nelems, int inc, int size,
+void *luaM_realloc (lua_State *L, void *oldblock, unsigned long size);
+void *luaM_growaux (lua_State *L, void *block, unsigned long nelems, int inc, int size,
                        const char *errormsg, unsigned long limit);
 
-#define luaM_free(b)	luaM_realloc((b), 0)
-#define luaM_malloc(t)	luaM_realloc(NULL, (t))
-#define luaM_new(t)          ((t *)luaM_malloc(sizeof(t)))
-#define luaM_newvector(n,t)  ((t *)luaM_malloc((n)*sizeof(t)))
-#define luaM_growvector(v,nelems,inc,t,e,l) \
-          ((v)=(t *)luaM_growaux(v,nelems,inc,sizeof(t),e,l))
-#define luaM_reallocvector(v,n,t) ((v)=(t *)luaM_realloc(v,(n)*sizeof(t)))
+#define luaM_free(L, b)	luaM_realloc(L, (b), 0)
+#define luaM_malloc(L, t)	luaM_realloc(L, NULL, (t))
+#define luaM_new(L, t)          ((t *)luaM_malloc(L, sizeof(t)))
+#define luaM_newvector(L, n,t)  ((t *)luaM_malloc(L, (n)*sizeof(t)))
+#define luaM_growvector(L, v,nelems,inc,t,e,l) \
+          ((v)=(t *)luaM_growaux(L, v,nelems,inc,sizeof(t),e,l))
+#define luaM_reallocvector(L, v,n,t) ((v)=(t *)luaM_realloc(L, v,(n)*sizeof(t)))
 
 
 #ifdef DEBUG

+ 6 - 4
lobject.c

@@ -1,5 +1,5 @@
 /*
-** $Id: lobject.c,v 1.23 1999/09/08 20:45:18 roberto Exp roberto $
+** $Id: lobject.c,v 1.24 1999/10/04 17:51:04 roberto Exp roberto $
 ** Some generic functions over Lua objects
 ** See Copyright Notice in lua.h
 */
@@ -7,6 +7,8 @@
 #include <ctype.h>
 #include <stdlib.h>
 
+#define LUA_REENTRANT
+
 #include "lobject.h"
 #include "lua.h"
 
@@ -28,13 +30,13 @@ static const long dimensions[] =
   1644817L, 3289613L, 6579211L, 13158023L, MAX_INT};
 
 
-int luaO_redimension (int oldsize) {
+int luaO_redimension (lua_State *L, int oldsize) {
   int i;
   for (i=0; dimensions[i]<MAX_INT; i++) {
     if (dimensions[i] > oldsize)
       return dimensions[i];
   }
-  lua_error("tableEM");
+  lua_error(L, "tableEM");
   return 0;  /* to avoid warnings */
 }
 
@@ -49,7 +51,7 @@ int luaO_equalval (const TObject *t1, const TObject *t2) {
     case LUA_T_CPROTO: return fvalue(t1)  == fvalue(t2);
     case LUA_T_CLOSURE: return t1->value.cl == t2->value.cl;
     default:
-     LUA_INTERNALERROR("invalid type");
+     LUA_INTERNALERROR(L, "invalid type");
      return 0; /* UNREACHABLE */
   }
 }

+ 10 - 10
lobject.h

@@ -1,5 +1,5 @@
 /*
-** $Id: lobject.h,v 1.35 1999/11/04 17:22:26 roberto Exp roberto $
+** $Id: lobject.h,v 1.36 1999/11/10 15:39:35 roberto Exp roberto $
 ** Type definitions for Lua objects
 ** See Copyright Notice in lua.h
 */
@@ -18,11 +18,11 @@
 #undef NDEBUG
 #endif
 #include <assert.h>
-#define LUA_INTERNALERROR(s)	assert(0)
-#define LUA_ASSERT(c,s)		assert(c)
+#define LUA_INTERNALERROR(L,s)	assert(0)
+#define LUA_ASSERT(L,c,s)	assert(c)
 #else
-#define LUA_INTERNALERROR(s)	/* empty */
-#define LUA_ASSERT(c,s)		/* empty */
+#define LUA_INTERNALERROR(L,s)	/* empty */
+#define LUA_ASSERT(L,c,s)		/* empty */
 #endif
 
 
@@ -41,11 +41,11 @@ typedef LUA_NUM_TYPE real;
 typedef unsigned char  Byte;  /* unsigned 8 bits */
 
 
-#define MAX_INT   (INT_MAX-2)  /* maximum value of an int (-2 for safety) */
+#define MAX_INT (INT_MAX-2)  /* maximum value of an int (-2 for safety) */
 
 
 /* convertion of pointer to int (for hashing only) */
-#define IntPoint(p)	((unsigned int)(p))
+#define IntPoint(L, p)	((unsigned int)(p))
 
 
 /*
@@ -53,7 +53,7 @@ typedef unsigned char  Byte;  /* unsigned 8 bits */
 ** objects count 1, and each 32 bytes of `raw' memory count 1; we add
 ** 2 to the total as a minimum (and also to count the overhead of malloc)
 */
-#define numblocks(o,b)	((o)+(b)/32+2)
+#define numblocks(L, o,b)	((o)+(b)/32+2)
 
 
 /*
@@ -195,7 +195,7 @@ typedef struct Hash {
 extern const char *const luaO_typenames[];
 
 
-#define luaO_typename(o)        luaO_typenames[-ttype(o)]
+#define luaO_typename(L, o)        luaO_typenames[-ttype(o)]
 
 
 extern const TObject luaO_nilobject;
@@ -204,7 +204,7 @@ extern const TObject luaO_nilobject;
 #define luaO_equalObj(t1,t2)	((ttype(t1) != ttype(t2)) ? 0 \
                                       : luaO_equalval(t1,t2))
 int luaO_equalval (const TObject *t1, const TObject *t2);
-int luaO_redimension (int oldsize);
+int luaO_redimension (lua_State *L, int oldsize);
 int luaO_str2d (const char *s, real *result);
 
 #ifdef OLD_ANSI

+ 61 - 56
lparser.c

@@ -1,5 +1,5 @@
 /*
-** $Id: lparser.c,v 1.41 1999/09/20 14:15:18 roberto Exp roberto $
+** $Id: lparser.c,v 1.42 1999/11/04 17:23:12 roberto Exp roberto $
 ** LL(1) Parser and code generator for Lua
 ** See Copyright Notice in lua.h
 */
@@ -147,14 +147,15 @@ static void checklimit (LexState *ls, int val, int limit, const char *msg) {
 }
 
 
-static void check_pc (FuncState *fs, int n) {
-  luaM_growvector(fs->f->code, fs->pc, n, Byte, codeEM, MAX_INT);
+static void check_pc (LexState *ls, int n) {
+  luaM_growvector(ls->L, ls->fs->f->code, ls->fs->pc, n,
+                  Byte, codeEM, MAX_INT);
 }
 
 
-static void code_byte (FuncState *fs, Byte c) {
-  check_pc(fs, 1);
-  fs->f->code[fs->pc++] = c;
+static void code_byte (LexState *ls, Byte c) {
+  check_pc(ls, 1);
+  ls->fs->f->code[ls->fs->pc++] = c;
 }
 
 
@@ -204,7 +205,7 @@ static int fix_opcode (LexState *ls, int pc, OpCode op, int arg) {
   if (tomove > 0) {  /* need to open space? */
     FuncState *fs = ls->fs;
     TProtoFunc *f = fs->f;
-    check_pc(fs, tomove);
+    check_pc(ls, tomove);
     luaO_memup(f->code+pc+tomove, f->code+pc, fs->pc-pc);
     fs->pc += tomove;
   }
@@ -215,7 +216,7 @@ static int fix_opcode (LexState *ls, int pc, OpCode op, int arg) {
 
 static void code_oparg (LexState *ls, OpCode op, int arg, int delta) {
   int size = codesize(arg);
-  check_pc(ls->fs, size);
+  check_pc(ls, size);
   code_oparg_at(ls, ls->fs->pc, op, arg, delta);
   ls->fs->pc += size;
 }
@@ -223,7 +224,7 @@ static void code_oparg (LexState *ls, OpCode op, int arg, int delta) {
 
 static void code_opcode (LexState *ls, OpCode op, int delta) {
   deltastack(ls, delta);
-  code_byte(ls->fs, (Byte)op);
+  code_byte(ls, (Byte)op);
 }
 
 
@@ -234,24 +235,24 @@ static void code_constant (LexState *ls, int c) {
 
 static void assertglobal (LexState *ls, int index) {
   TObject *o = &ls->fs->f->consts[index];
-  LUA_ASSERT(ttype(o) == LUA_T_STRING, "global name is not a string");
-  luaS_assertglobal(tsvalue(o));
+  LUA_ASSERT(ls->L, ttype(o) == LUA_T_STRING, "global name is not a string");
+  luaS_assertglobal(ls->L, tsvalue(o));
 }
 
 
-static int next_constant (FuncState *fs) {
-  TProtoFunc *f = fs->f;
-  luaM_growvector(f->consts, f->nconsts, 1, TObject, constantEM, MAX_ARG);
+static int next_constant (LexState *ls, TProtoFunc *f) {
+  luaM_growvector(ls->L, f->consts, f->nconsts, 1,
+                  TObject, constantEM, MAX_ARG);
   return f->nconsts++;
 }
 
 
-static int string_constant (FuncState *fs, TaggedString *s) {
+static int string_constant (LexState *ls, FuncState *fs, TaggedString *s) {
   TProtoFunc *f = fs->f;
   int c = s->constindex;
   if (!(c < f->nconsts &&
       ttype(&f->consts[c]) == LUA_T_STRING && tsvalue(&f->consts[c]) == s)) {
-    c = next_constant(fs);
+    c = next_constant(ls, f);
     ttype(&f->consts[c]) = LUA_T_STRING;
     tsvalue(&f->consts[c]) = s;
     s->constindex = c;  /* hint for next time */
@@ -261,23 +262,24 @@ static int string_constant (FuncState *fs, TaggedString *s) {
 
 
 static void code_string (LexState *ls, TaggedString *s) {
-  code_constant(ls, string_constant(ls->fs, s));
+  code_constant(ls, string_constant(ls, ls->fs, s));
 }
 
 
 #define LIM 20
-static int real_constant (FuncState *fs, real r) {
+static int real_constant (LexState *ls, real r) {
   /* check whether 'r' has appeared within the last LIM entries */
-  TObject *cnt = fs->f->consts;
-  int c = fs->f->nconsts;
+  TProtoFunc *f = ls->fs->f;
+  TObject *cnt = f->consts;
+  int c = f->nconsts;
   int lim = c < LIM ? 0 : c-LIM;
   while (--c >= lim) {
     if (ttype(&cnt[c]) == LUA_T_NUMBER && nvalue(&cnt[c]) == r)
       return c;
   }
   /* not found; create a new entry */
-  c = next_constant(fs);
-  cnt = fs->f->consts;  /* 'next_constant' may have reallocated this vector */
+  c = next_constant(ls, f);
+  cnt = f->consts;  /* 'next_constant' may reallocate this vector */
   ttype(&cnt[c]) = LUA_T_NUMBER;
   nvalue(&cnt[c]) = r;
   return c;
@@ -291,7 +293,7 @@ static void code_number (LexState *ls, real f) {
     code_oparg(ls, (f<0) ? PUSHNUMBERNEG : PUSHNUMBER, (int)af, 1);
   }
   else
-    code_constant(ls, real_constant(ls->fs, f));
+    code_constant(ls, real_constant(ls, f));
 }
 
 
@@ -304,16 +306,17 @@ static void flush_record (LexState *ls, int n) {
 static void flush_list (LexState *ls, int m, int n) {
   if (n > 0) {
     code_oparg(ls, SETLIST, m, -n);
-    code_byte(ls->fs, (Byte)n);
+    code_byte(ls, (Byte)n);
   }
 }
 
 
-static void luaI_registerlocalvar (FuncState *fs, TaggedString *varname,
+static void luaI_registerlocalvar (LexState *ls, TaggedString *varname,
                                    int line) {
+  FuncState *fs = ls->fs;
   if (fs->nvars != -1) {  /* debug information? */
     TProtoFunc *f = fs->f;
-    luaM_growvector(f->locvars, fs->nvars, 1, LocVar, "", MAX_INT);
+    luaM_growvector(ls->L, f->locvars, fs->nvars, 1, LocVar, "", MAX_INT);
     f->locvars[fs->nvars].varname = varname;
     f->locvars[fs->nvars].line = line;
     fs->nvars++;
@@ -321,8 +324,8 @@ static void luaI_registerlocalvar (FuncState *fs, TaggedString *varname,
 }
 
 
-static void luaI_unregisterlocalvar (FuncState *fs, int line) {
-  luaI_registerlocalvar(fs, NULL, line);
+static void luaI_unregisterlocalvar (LexState *ls, int line) {
+  luaI_registerlocalvar(ls, NULL, line);
 }
 
 
@@ -330,7 +333,7 @@ static void store_localvar (LexState *ls, TaggedString *name, int n) {
   FuncState *fs = ls->fs;
   checklimit(ls, fs->nlocalvar+n+1, MAXLOCALS, "local variables");
   fs->localvar[fs->nlocalvar+n] = name;
-  luaI_registerlocalvar(fs, name, ls->linenumber);
+  luaI_registerlocalvar(ls, name, ls->linenumber);
 }
 
 
@@ -371,7 +374,7 @@ static void singlevar (LexState *ls, TaggedString *n, vardesc *var, int prev) {
       if (aux_localname(level, n) >= 0)
         luaX_syntaxerror(ls, "cannot access a variable in outer scope", n->str);
     var->k = VGLOBAL;
-    var->info = string_constant(fs, n);
+    var->info = string_constant(ls, fs, n);
   }
 }
 
@@ -404,7 +407,7 @@ static void pushupvalue (LexState *ls, TaggedString *n) {
 
 
 static void check_debugline (LexState *ls) {
-  if (L->debug && ls->linenumber != ls->fs->lastsetline) {
+  if (ls->L->debug && ls->linenumber != ls->fs->lastsetline) {
     code_oparg(ls, SETLINE, ls->linenumber, 0);
     ls->fs->lastsetline = ls->linenumber;
   }
@@ -464,7 +467,7 @@ static void code_args (LexState *ls, int nparams, int dots) {
   else {
     fs->f->code[1] = (Byte)(nparams+ZEROVARARG);
     deltastack(ls, nparams+1);
-    add_localvar(ls, luaS_new("arg"));
+    add_localvar(ls, luaS_new(ls->L, "arg"));
   }
 }
 
@@ -515,7 +518,7 @@ static void storevar (LexState *ls, const vardesc *var) {
       code_opcode(ls, SETTABLEPOP, -3);
       break;
     default:
-      LUA_INTERNALERROR("invalid var kind to store");
+      LUA_INTERNALERROR(ls->L, "invalid var kind to store");
   }
 }
 
@@ -548,7 +551,7 @@ static void codeIf (LexState *ls, int thenAdd, int elseAdd) {
 static void func_onstack (LexState *ls, FuncState *func) {
   FuncState *fs = ls->fs;
   int i;
-  int c = next_constant(fs);
+  int c = next_constant(ls, fs->f);
   ttype(&fs->f->consts[c]) = LUA_T_PROTO;
   fs->f->consts[c].value.tf = func->f;
   if (func->nupvalues == 0)
@@ -558,13 +561,14 @@ static void func_onstack (LexState *ls, FuncState *func) {
       lua_pushvar(ls, &func->upvalues[i]);
     deltastack(ls, 1);  /* CLOSURE puts one extra element (before poping) */
     code_oparg(ls, CLOSURE, c, -func->nupvalues);
-    code_byte(fs, (Byte)func->nupvalues);
+    code_byte(ls, (Byte)func->nupvalues);
   }
 }
 
 
 static void init_state (LexState *ls, FuncState *fs, TaggedString *source) {
-  TProtoFunc *f = luaF_newproto();
+  lua_State *L = ls->L;
+  TProtoFunc *f = luaF_newproto(ls->L);
   fs->prev = ls->fs;  /* linked list of funcstates */
   ls->fs = fs;
   fs->stacksize = 0;
@@ -577,10 +581,11 @@ static void init_state (LexState *ls, FuncState *fs, TaggedString *source) {
   fs->pc = 0;
   f->code = NULL;
   fs->nvars = (L->debug) ? 0 : -1;  /* flag no debug information? */
-  code_byte(fs, 0);  /* to be filled with maxstacksize */
-  code_byte(fs, 0);  /* to be filled with arg information */
+  code_byte(ls, 0);  /* to be filled with maxstacksize */
+  code_byte(ls, 0);  /* to be filled with arg information */
   /* push function (to avoid GC) */
-  tfvalue(L->stack.top) = f; ttype(L->stack.top) = LUA_T_PROTO;
+  tfvalue(L->stack.top) = f;
+  ttype(L->stack.top) = LUA_T_PROTO;
   incr_top;
 }
 
@@ -590,14 +595,14 @@ static void close_func (LexState *ls) {
   TProtoFunc *f = fs->f;
   code_opcode(ls, ENDCODE, 0);
   f->code[0] = (Byte)fs->maxstacksize;
-  luaM_reallocvector(f->code, fs->pc, Byte);
-  luaM_reallocvector(f->consts, f->nconsts, TObject);
+  luaM_reallocvector(ls->L, f->code, fs->pc, Byte);
+  luaM_reallocvector(ls->L, f->consts, f->nconsts, TObject);
   if (fs->nvars != -1) {  /* debug information? */
-    luaI_registerlocalvar(fs, NULL, -1);  /* flag end of vector */
-    luaM_reallocvector(f->locvars, fs->nvars, LocVar);
+    luaI_registerlocalvar(ls, NULL, -1);  /* flag end of vector */
+    luaM_reallocvector(ls->L, f->locvars, fs->nvars, LocVar);
   }
   ls->fs = fs->prev;
-  L->stack.top--;  /* pop function */
+  ls->L->stack.top--;  /* pop function */
 }
 
 
@@ -664,7 +669,7 @@ static int checkname (LexState *ls) {
   int sc;
   if (ls->token != NAME)
     luaX_error(ls, "`NAME' expected");
-  sc = string_constant(ls->fs, ls->seminfo.ts);
+  sc = string_constant(ls, ls->fs, ls->seminfo.ts);
   next(ls);
   return sc;
 }
@@ -685,11 +690,11 @@ static int optional (LexState *ls, int c) {
 }
 
 
-TProtoFunc *luaY_parser (ZIO *z) {
+TProtoFunc *luaY_parser (lua_State *L, ZIO *z) {
   struct LexState lexstate;
   struct FuncState funcstate;
-  luaX_setinput(&lexstate, z);
-  init_state(&lexstate, &funcstate, luaS_new(zname(z)));
+  luaX_setinput(L, &lexstate, z);
+  init_state(&lexstate, &funcstate, luaS_new(L, zname(z)));
   next(&lexstate);  /* read first token */
   chunk(&lexstate);
   if (lexstate.token != EOS)
@@ -708,7 +713,7 @@ TProtoFunc *luaY_parser (ZIO *z) {
 static void chunk (LexState *ls) {
   /* chunk -> { stat [;] } ret */
   while (stat(ls)) {
-    LUA_ASSERT(ls->fs->stacksize == ls->fs->nlocalvar,
+    LUA_ASSERT(ls->L, ls->fs->stacksize == ls->fs->nlocalvar,
                "stack size != # local vars");
     optional(ls, ';');
   }
@@ -728,7 +733,7 @@ static void whilestat (LexState *ls, int line) {
   block(ls);
   check_match(ls, END, WHILE, line);
   cond_size = cond_end-while_init;
-  check_pc(fs, cond_size);
+  check_pc(ls, cond_size);
   memcpy(f->code+fs->pc, f->code+while_init, cond_size);
   luaO_memdown(f->code+while_init, f->code+cond_end, fs->pc-while_init);
   while_init += JMPSIZE + fix_jump(ls, while_init, JMP, fs->pc-cond_size);
@@ -841,7 +846,7 @@ static int stat (LexState *ls) {
 
 static int SaveWord (LexState *ls) {
   int res = ls->fs->pc;
-  check_pc(ls->fs, JMPSIZE);
+  check_pc(ls, JMPSIZE);
   ls->fs->pc += JMPSIZE;  /* open space */
   return res;
 }
@@ -864,7 +869,7 @@ static void block (LexState *ls) {
   chunk(ls);
   adjuststack(ls, fs->nlocalvar - nlocalvar);
   for (; fs->nlocalvar > nlocalvar; fs->nlocalvar--)
-    luaI_unregisterlocalvar(fs, fs->lastsetline);
+    luaI_unregisterlocalvar(ls, fs->lastsetline);
 }
 
 static int funcname (LexState *ls, vardesc *v) {
@@ -888,7 +893,7 @@ static void body (LexState *ls, int needself, int line) {
   newfs.f->lineDefined = line;
   check(ls, '(');
   if (needself)
-    add_localvar(ls, luaS_new("self"));
+    add_localvar(ls, luaS_new(ls->L, "self"));
   parlist(ls);
   check(ls, ')');
   chunk(ls);
@@ -1173,9 +1178,9 @@ static int funcparams (LexState *ls, int slf) {
       luaX_error(ls, "function arguments expected");
       break;
   }
-  code_byte(fs, CALL);
-  code_byte(fs, 0);  /* save space for nresult */
-  code_byte(fs, (Byte)(nparams+slf));
+  code_byte(ls, CALL);
+  code_byte(ls, 0);  /* save space for nresult */
+  code_byte(ls, (Byte)(nparams+slf));
   return fs->pc-1;
 }
 

+ 2 - 5
lparser.h

@@ -1,5 +1,5 @@
 /*
-** $Id: lparser.h,v 1.3 1999/02/25 19:13:56 roberto Exp roberto $
+** $Id: lparser.h,v 1.4 1999/08/16 20:52:00 roberto Exp roberto $
 ** LL(1) Parser and code generator for Lua
 ** See Copyright Notice in lua.h
 */
@@ -11,10 +11,7 @@
 #include "lzio.h"
 
 
-void luaY_codedebugline (int line);
-TProtoFunc *luaY_parser (ZIO *z);
-void luaY_error (const char *s);
-void luaY_syntaxerror (const char *s, const char *token);
+TProtoFunc *luaY_parser (lua_State *L, ZIO *z);
 
 
 #endif

+ 14 - 12
lref.c

@@ -1,17 +1,19 @@
 /*
-** $Id: lref.c,v 1.1 1999/10/04 17:50:24 roberto Exp roberto $
+** $Id: lref.c,v 1.2 1999/11/10 15:37:50 roberto Exp roberto $
 ** REF mechanism
 ** See Copyright Notice in lua.h
 */
 
 
+#define LUA_REENTRANT
+
 #include "lmem.h"
 #include "lref.h"
 #include "lstate.h"
 #include "lua.h"
 
 
-int luaR_ref (const TObject *o, int lock) {
+int luaR_ref (lua_State *L, const TObject *o, int lock) {
   int ref;
   if (ttype(o) == LUA_T_NIL)
     ref = LUA_REFNIL;
@@ -21,7 +23,7 @@ int luaR_ref (const TObject *o, int lock) {
       L->refFree = L->refArray[ref].st;
     }
     else {  /* no more free places */
-      luaM_growvector(L->refArray, L->refSize, 1, struct ref, refEM, MAX_INT);
+      luaM_growvector(L, L->refArray, L->refSize, 1, struct ref, refEM, MAX_INT);
       ref = L->refSize++;
     }
     L->refArray[ref].o = *o;
@@ -31,17 +33,17 @@ int luaR_ref (const TObject *o, int lock) {
 }
 
 
-void lua_unref (int ref) {
+void lua_unref (lua_State *L, int ref) {
   if (ref >= 0) {
     if (ref >= L->refSize || L->refArray[ref].st >= 0)
-      lua_error("API error - invalid parameter for function `lua_unref'");
+      lua_error(L, "API error - invalid parameter for function `lua_unref'");
     L->refArray[ref].st = L->refFree;
     L->refFree = ref;
   }
 }
 
 
-const TObject *luaR_getref (int ref) {
+const TObject *luaR_getref (lua_State *L, int ref) {
   if (ref == LUA_REFNIL)
     return &luaO_nilobject;
   else if (0 <= ref && ref < L->refSize &&
@@ -66,7 +68,7 @@ static int ismarked (const TObject *o) {
 #ifdef DEBUG
     case LUA_T_LINE: case LUA_T_CLMARK:
     case LUA_T_CMARK: case LUA_T_PMARK:
-      LUA_INTERNALERROR("invalid type");
+      LUA_INTERNALERROR(L, "invalid type");
 #endif
     default:  /* number or cproto */
       return 1;
@@ -75,21 +77,21 @@ static int ismarked (const TObject *o) {
 
 
 /* for internal debugging only; check if a link of free refs is valid */
-#define VALIDLINK(st,n)	(NONEXT <= (st) && (st) < (n))
+#define VALIDLINK(L, st,n)	(NONEXT <= (st) && (st) < (n))
 
-void luaR_invalidaterefs (void) {
+void luaR_invalidaterefs (lua_State *L) {
   int n = L->refSize;
   int i;
   for (i=0; i<n; i++) {
     struct ref *r = &L->refArray[i];
     if (r->st == HOLD && !ismarked(&r->o))
       r->st = COLLECTED;
-    LUA_ASSERT((r->st == LOCK && ismarked(&r->o)) ||
+    LUA_ASSERT(L, (r->st == LOCK && ismarked(&r->o)) ||
                 r->st == COLLECTED ||
                 r->st == NONEXT ||
-               (r->st < n && VALIDLINK(L->refArray[r->st].st, n)),
+               (r->st < n && VALIDLINK(L, L->refArray[r->st].st, n)),
                "inconsistent ref table");
   }
-  LUA_ASSERT(VALIDLINK(L->refFree, n), "inconsistent ref table");
+  LUA_ASSERT(L, VALIDLINK(L, L->refFree, n), "inconsistent ref table");
 }
 

+ 4 - 4
lref.h

@@ -1,5 +1,5 @@
 /*
-** $Id: lref.h,v 1.1 1999/10/04 17:50:24 roberto Exp roberto $
+** $Id: lref.h,v 1.2 1999/11/10 15:37:50 roberto Exp roberto $
 ** REF mechanism
 ** See Copyright Notice in lua.h
 */
@@ -22,9 +22,9 @@ struct ref {
 };
 
 
-int luaR_ref (const TObject *o, int lock);
-const TObject *luaR_getref (int ref);
-void luaR_invalidaterefs (void);
+int luaR_ref (lua_State *L, const TObject *o, int lock);
+const TObject *luaR_getref (lua_State *L, int ref);
+void luaR_invalidaterefs (lua_State *L);
 
 
 #endif

+ 27 - 25
lstate.c

@@ -1,10 +1,12 @@
 /*
-** $Id: lstate.c,v 1.15 1999/10/14 17:53:35 roberto Exp roberto $
+** $Id: lstate.c,v 1.16 1999/11/10 15:39:35 roberto Exp roberto $
 ** Global State
 ** See Copyright Notice in lua.h
 */
 
 
+#define LUA_REENTRANT
+
 #include "lbuiltin.h"
 #include "ldo.h"
 #include "lgc.h"
@@ -19,9 +21,8 @@
 lua_State *lua_state = NULL;
 
 
-void lua_open (void) {
-  if (lua_state) return;
-  lua_state = luaM_new(lua_State);
+lua_State *lua_newstate (void) {
+  lua_State *L = luaM_new(NULL, lua_State);
   L->Cstack.base = 0;
   L->Cstack.lua2C = 0;
   L->Cstack.num = 0;
@@ -45,31 +46,32 @@ void lua_open (void) {
   L->refFree = NONEXT;
   L->nblocks = 0;
   L->GCthreshold = MAX_INT;  /* to avoid GC during pre-definitions */
-  luaD_init();
-  luaS_init();
-  luaX_init();
-  luaT_init();
-  luaB_predefine();
+  luaD_init(L);
+  luaS_init(L);
+  luaX_init(L);
+  luaT_init(L);
+  luaB_predefine(L);
+  return L;
   L->GCthreshold = L->nblocks*4;
 }
 
 
-void lua_close (void) {
-  luaC_collect(1);  /* collect all elements */
-  LUA_ASSERT(L->rootproto == NULL, "list should be empty");
-  LUA_ASSERT(L->rootcl == NULL, "list should be empty");
-  LUA_ASSERT(L->rootglobal == NULL, "list should be empty");
-  LUA_ASSERT(L->roottable == NULL, "list should be empty");
-  luaS_freeall();
-  luaM_free(L->stack.stack);
-  luaM_free(L->IMtable);
-  luaM_free(L->refArray);
-  luaM_free(L->Mbuffer);
-  luaM_free(L->Cblocks);
-  LUA_ASSERT(L->nblocks == 0, "wrong count for nblocks");
-  luaM_free(L);
-  LUA_ASSERT(numblocks == 0, "memory leak!");
-  LUA_ASSERT(totalmem == 0,"memory leak!");
+void lua_close (lua_State *L) {
+  luaC_collect(L, 1);  /* collect all elements */
+  LUA_ASSERT(L, L->rootproto == NULL, "list should be empty");
+  LUA_ASSERT(L, L->rootcl == NULL, "list should be empty");
+  LUA_ASSERT(L, L->rootglobal == NULL, "list should be empty");
+  LUA_ASSERT(L, L->roottable == NULL, "list should be empty");
+  luaS_freeall(L);
+  luaM_free(L, L->stack.stack);
+  luaM_free(L, L->IMtable);
+  luaM_free(L, L->refArray);
+  luaM_free(L, L->Mbuffer);
+  luaM_free(L, L->Cblocks);
+  LUA_ASSERT(L, L->nblocks == 0, "wrong count for nblocks");
+  luaM_free(L, L);
+  LUA_ASSERT(L, numblocks == 0, "memory leak!");
+  LUA_ASSERT(L, totalmem == 0,"memory leak!");
   L = NULL;
 }
 

+ 2 - 2
lstate.h

@@ -1,5 +1,5 @@
 /*
-** $Id: lstate.h,v 1.21 1999/11/04 17:22:26 roberto Exp roberto $
+** $Id: lstate.h,v 1.22 1999/11/10 15:39:35 roberto Exp roberto $
 ** Global State
 ** See Copyright Notice in lua.h
 */
@@ -79,7 +79,7 @@ struct lua_State {
 };
 
 
-#define L	lua_state
+
 
 
 #endif

+ 48 - 46
lstring.c

@@ -1,5 +1,5 @@
 /*
-** $Id: lstring.c,v 1.26 1999/11/04 17:22:26 roberto Exp roberto $
+** $Id: lstring.c,v 1.27 1999/11/10 15:39:35 roberto Exp roberto $
 ** String table (keeps all strings handled by Lua)
 ** See Copyright Notice in lua.h
 */
@@ -7,6 +7,8 @@
 
 #include <string.h>
 
+#define LUA_REENTRANT
+
 #include "lmem.h"
 #include "lobject.h"
 #include "lstate.h"
@@ -15,8 +17,8 @@
 
 
 
-#define gcsizestring(l)	numblocks(0, sizeof(TaggedString)+l)
-#define gcsizeudata	gcsizestring(0)
+#define gcsizestring(L, l)	numblocks(L, 0, sizeof(TaggedString)+l)
+#define gcsizeudata	gcsizestring(L, 0)
 
 
 
@@ -30,9 +32,9 @@
 static TaggedString *init_hash[1] = {NULL};
 
 
-void luaS_init (void) {
+void luaS_init (lua_State *L) {
   int i;
-  L->string_root = luaM_newvector(NUM_HASHS, stringtable);
+  L->string_root = luaM_newvector(L, NUM_HASHS, stringtable);
   for (i=0; i<NUM_HASHS; i++) {
     L->string_root[i].size = 1;
     L->string_root[i].nuse = 0;
@@ -41,15 +43,15 @@ void luaS_init (void) {
 }
 
 
-void luaS_freeall (void) {
+void luaS_freeall (lua_State *L) {
   int i;
   for (i=0; i<NUM_HASHS; i++) {
-    LUA_ASSERT(L->string_root[i].nuse==0, "non-empty string table");
+    LUA_ASSERT(L, L->string_root[i].nuse==0, "non-empty string table");
     if (L->string_root[i].hash != init_hash)
-      luaM_free(L->string_root[i].hash);
+      luaM_free(L, L->string_root[i].hash);
   }
-  luaM_free(L->string_root);
-  LUA_ASSERT(init_hash[0] == NULL, "init_hash corrupted");
+  luaM_free(L, L->string_root);
+  LUA_ASSERT(L, init_hash[0] == NULL, "init_hash corrupted");
 }
 
 
@@ -61,9 +63,9 @@ static unsigned long hash_s (const char *s, long l) {
 }
 
 
-void luaS_grow (stringtable *tb) {
-  int ns = luaO_redimension(tb->nuse*2);  /* new size */
-  TaggedString **newhash = luaM_newvector(ns, TaggedString *);
+void luaS_grow (lua_State *L, stringtable *tb) {
+  int ns = luaO_redimension(L, tb->nuse*2);  /* new size */
+  TaggedString **newhash = luaM_newvector(L, ns, TaggedString *);
   int i;
   for (i=0; i<ns; i++) newhash[i] = NULL;
   /* rehash */
@@ -77,14 +79,14 @@ void luaS_grow (stringtable *tb) {
       p = next;
     }
   }
-  luaM_free(tb->hash);
+  luaM_free(L, tb->hash);
   tb->size = ns;
   tb->hash = newhash;
 }
 
 
-static TaggedString *newone (long l, unsigned long h) {
-  TaggedString *ts = (TaggedString *)luaM_malloc(
+static TaggedString *newone (lua_State *L, long l, unsigned long h) {
+  TaggedString *ts = (TaggedString *)luaM_malloc(L, 
                                        sizeof(TaggedString)+l*sizeof(char));
   ts->marked = 0;
   ts->nexthash = NULL;
@@ -93,20 +95,20 @@ static TaggedString *newone (long l, unsigned long h) {
 }
 
 
-static TaggedString *newone_s (const char *str, long l, unsigned long h) {
-  TaggedString *ts = newone(l, h);
+static TaggedString *newone_s (lua_State *L, const char *str, long l, unsigned long h) {
+  TaggedString *ts = newone(L, l, h);
   memcpy(ts->str, str, l);
   ts->str[l] = 0;  /* ending 0 */
   ts->u.s.gv = NULL;  /* no global value */
   ts->u.s.len = l;
   ts->constindex = 0;
-  L->nblocks += gcsizestring(l);
+  L->nblocks += gcsizestring(L, l);
   return ts;
 }
 
 
-static TaggedString *newone_u (void *buff, int tag, unsigned long h) {
-  TaggedString *ts = newone(0, h);
+static TaggedString *newone_u (lua_State *L, void *buff, int tag, unsigned long h) {
+  TaggedString *ts = newone(L, 0, h);
   ts->u.d.value = buff;
   ts->u.d.tag = (tag == LUA_ANYTAG) ? 0 : tag;
   ts->constindex = -1;  /* tag -> this is a userdata */
@@ -115,15 +117,15 @@ static TaggedString *newone_u (void *buff, int tag, unsigned long h) {
 }
 
 
-static void newentry (stringtable *tb, TaggedString *ts, int h) {
+static void newentry (lua_State *L, stringtable *tb, TaggedString *ts, int h) {
   tb->nuse++;
   if (tb->nuse >= tb->size) {  /* no more room? */
     if (tb->hash == init_hash) {  /* cannot change init_hash */
-      LUA_ASSERT(h==0, "`init_hash' has size 1");
-      tb->hash = luaM_newvector(1, TaggedString *);  /* so, `clone' it */
+      LUA_ASSERT(L, h==0, "`init_hash' has size 1");
+      tb->hash = luaM_newvector(L, 1, TaggedString *);  /* so, `clone' it */
       tb->hash[0] = NULL;
     }
-    luaS_grow(tb);
+    luaS_grow(L, tb);
     h = ts->hash%tb->size;  /* new hash position */
   }
   ts->nexthash = tb->hash[h];  /* chain new entry */
@@ -131,7 +133,7 @@ static void newentry (stringtable *tb, TaggedString *ts, int h) {
 }
 
 
-TaggedString *luaS_newlstr (const char *str, long l) {
+TaggedString *luaS_newlstr (lua_State *L, const char *str, long l) {
   unsigned long h = hash_s(str, l);
   stringtable *tb = &L->string_root[h%NUM_HASHSTR];
   int h1 = h%tb->size;
@@ -141,14 +143,14 @@ TaggedString *luaS_newlstr (const char *str, long l) {
       return ts;
   }
   /* not found */
-  ts = newone_s(str, l, h);  /* create new entry */
-  newentry(tb, ts, h1);  /* insert it on table */
+  ts = newone_s(L, str, l, h);  /* create new entry */
+  newentry(L, tb, ts, h1);  /* insert it on table */
   return ts;
 }
 
 
-TaggedString *luaS_createudata (void *udata, int tag) {
-  unsigned long h = IntPoint(udata);
+TaggedString *luaS_createudata (lua_State *L, void *udata, int tag) {
+  unsigned long h = IntPoint(L, udata);
   stringtable *tb = &L->string_root[(h%NUM_HASHUDATA)+NUM_HASHSTR];
   int h1 = h%tb->size;
   TaggedString *ts;
@@ -157,38 +159,38 @@ TaggedString *luaS_createudata (void *udata, int tag) {
       return ts;
   }
   /* not found */
-  ts = newone_u(udata, tag, h);
-  newentry(tb, ts, h1);
+  ts = newone_u(L, udata, tag, h);
+  newentry(L, tb, ts, h1);
   return ts;
 }
 
 
-TaggedString *luaS_new (const char *str) {
-  return luaS_newlstr(str, strlen(str));
+TaggedString *luaS_new (lua_State *L, const char *str) {
+  return luaS_newlstr(L, str, strlen(str));
 }
 
-TaggedString *luaS_newfixedstring (const char *str) {
-  TaggedString *ts = luaS_new(str);
+TaggedString *luaS_newfixedstring (lua_State *L, const char *str) {
+  TaggedString *ts = luaS_new(L, str);
   if (ts->marked == 0) ts->marked = FIXMARK;  /* avoid GC */
   return ts;
 }
 
 
-void luaS_free (TaggedString *t) {
+void luaS_free (lua_State *L, TaggedString *t) {
   if (t->constindex == -1)  /* is userdata? */
     L->nblocks -= gcsizeudata;
   else {  /* is string */
-    L->nblocks -= gcsizestring(t->u.s.len);
-    luaM_free(t->u.s.gv);
+    L->nblocks -= gcsizestring(L, t->u.s.len);
+    luaM_free(L, t->u.s.gv);
   }
-  luaM_free(t);
+  luaM_free(L, t);
 }
 
 
-GlobalVar *luaS_assertglobal (TaggedString *ts) {
+GlobalVar *luaS_assertglobal (lua_State *L, TaggedString *ts) {
   GlobalVar *gv = ts->u.s.gv;
   if (!gv) {  /* no global value yet? */
-    gv = luaM_new(GlobalVar);
+    gv = luaM_new(L, GlobalVar);
     gv->value.ttype = LUA_T_NIL;  /* initial value */
     gv->name = ts;
     gv->next = L->rootglobal;  /* chain in global list */
@@ -199,13 +201,13 @@ GlobalVar *luaS_assertglobal (TaggedString *ts) {
 }
 
 
-GlobalVar *luaS_assertglobalbyname (const char *name) {
-  return luaS_assertglobal(luaS_new(name));
+GlobalVar *luaS_assertglobalbyname (lua_State *L, const char *name) {
+  return luaS_assertglobal(L, luaS_new(L, name));
 }
 
 
-int luaS_globaldefined (const char *name) {
-  TaggedString *ts = luaS_new(name);
+int luaS_globaldefined (lua_State *L, const char *name) {
+  TaggedString *ts = luaS_new(L, name);
   return ts->u.s.gv && ts->u.s.gv->value.ttype != LUA_T_NIL;
 }
 

+ 13 - 13
lstring.h

@@ -1,5 +1,5 @@
 /*
-** $Id: lstring.h,v 1.11 1999/10/14 19:13:31 roberto Exp roberto $
+** $Id: lstring.h,v 1.12 1999/11/04 17:22:26 roberto Exp roberto $
 ** String table (keep all strings handled by Lua)
 ** See Copyright Notice in lua.h
 */
@@ -14,7 +14,7 @@
 
 #define NUM_HASHSTR     31  /* a prime not in array `dimensions' */
 #define NUM_HASHUDATA   31  /* idem */
-#define NUM_HASHS  (NUM_HASHSTR+NUM_HASHUDATA)
+#define NUM_HASHS (NUM_HASHSTR+NUM_HASHUDATA)
 
 
 /*
@@ -25,17 +25,17 @@
 #define RESERVEDMARK	3
 
 
-void luaS_init (void);
-void luaS_grow (stringtable *tb);
-TaggedString *luaS_createudata (void *udata, int tag);
-void luaS_freeall (void);
-void luaS_free (TaggedString *ts);
-TaggedString *luaS_newlstr (const char *str, long l);
-TaggedString *luaS_new (const char *str);
-TaggedString *luaS_newfixedstring (const char *str);
-GlobalVar *luaS_assertglobal (TaggedString *ts);
-GlobalVar *luaS_assertglobalbyname (const char *name);
-int luaS_globaldefined (const char *name);
+void luaS_init (lua_State *L);
+void luaS_grow (lua_State *L, stringtable *tb);
+TaggedString *luaS_createudata (lua_State *L, void *udata, int tag);
+void luaS_freeall (lua_State *L);
+void luaS_free (lua_State *L, TaggedString *ts);
+TaggedString *luaS_newlstr (lua_State *L, const char *str, long l);
+TaggedString *luaS_new (lua_State *L, const char *str);
+TaggedString *luaS_newfixedstring (lua_State *L, const char *str);
+GlobalVar *luaS_assertglobal (lua_State *L, TaggedString *ts);
+GlobalVar *luaS_assertglobalbyname (lua_State *L, const char *name);
+int luaS_globaldefined (lua_State *L, const char *name);
 
 
 #endif

+ 156 - 154
lstrlib.c

@@ -1,5 +1,5 @@
 /*
-** $Id: lstrlib.c,v 1.35 1999/10/25 13:35:44 roberto Exp roberto $
+** $Id: lstrlib.c,v 1.36 1999/11/11 16:45:04 roberto Exp roberto $
 ** Standard library for strings and pattern-matching
 ** See Copyright Notice in lua.h
 */
@@ -10,28 +10,30 @@
 #include <stdlib.h>
 #include <string.h>
 
+#define LUA_REENTRANT
+
 #include "lauxlib.h"
 #include "lua.h"
 #include "lualib.h"
 
 
 
-static void addnchar (const char *s, int n) {
-  char *b = luaL_openspace(n);
+static void addnchar (lua_State *L, const char *s, int n) {
+  char *b = luaL_openspace(L, n);
   memcpy(b, s, n);
-  luaL_addsize(n);
+  luaL_addsize(L, n);
 }
 
 
-static void str_len (void) {
+static void str_len (lua_State *L) {
   long l;
-  luaL_check_lstr(1, &l);
-  lua_pushnumber(l);
+  luaL_check_lstr(L, 1, &l);
+  lua_pushnumber(L, l);
 }
 
 
-static void closeandpush (void) {
-  lua_pushlstring(luaL_buffer(), luaL_getsize());
+static void closeandpush (lua_State *L) {
+  lua_pushlstring(L, luaL_buffer(L), luaL_getsize(L));
 }
 
 
@@ -41,69 +43,69 @@ static long posrelat (long pos, long len) {
 }
 
 
-static void str_sub (void) {
+static void str_sub (lua_State *L) {
   long l;
-  const char *s = luaL_check_lstr(1, &l);
-  long start = posrelat(luaL_check_long(2), l);
-  long end = posrelat(luaL_opt_long(3, -1), l);
+  const char *s = luaL_check_lstr(L, 1, &l);
+  long start = posrelat(luaL_check_long(L, 2), l);
+  long end = posrelat(luaL_opt_long(L, 3, -1), l);
   if (start < 1) start = 1;
   if (end > l) end = l;
   if (start <= end)
-    lua_pushlstring(s+start-1, end-start+1);
-  else lua_pushstring("");
+    lua_pushlstring(L, s+start-1, end-start+1);
+  else lua_pushstring(L, "");
 }
 
 
-static void str_lower (void) {
+static void str_lower (lua_State *L) {
   long l;
   int i;
-  const char *s = luaL_check_lstr(1, &l);
-  luaL_resetbuffer();
+  const char *s = luaL_check_lstr(L, 1, &l);
+  luaL_resetbuffer(L);
   for (i=0; i<l; i++)
-    luaL_addchar(tolower((unsigned char)(s[i])));
-  closeandpush();
+    luaL_addchar(L, tolower((unsigned char)(s[i])));
+  closeandpush(L);
 }
 
 
-static void str_upper (void) {
+static void str_upper (lua_State *L) {
   long l;
   int i;
-  const char *s = luaL_check_lstr(1, &l);
-  luaL_resetbuffer();
+  const char *s = luaL_check_lstr(L, 1, &l);
+  luaL_resetbuffer(L);
   for (i=0; i<l; i++)
-    luaL_addchar(toupper((unsigned char)(s[i])));
-  closeandpush();
+    luaL_addchar(L, toupper((unsigned char)(s[i])));
+  closeandpush(L);
 }
 
-static void str_rep (void) {
+static void str_rep (lua_State *L) {
   long l;
-  const char *s = luaL_check_lstr(1, &l);
-  int n = luaL_check_int(2);
-  luaL_resetbuffer();
+  const char *s = luaL_check_lstr(L, 1, &l);
+  int n = luaL_check_int(L, 2);
+  luaL_resetbuffer(L);
   while (n-- > 0)
-    addnchar(s, l);
-  closeandpush();
+    addnchar(L, s, l);
+  closeandpush(L);
 }
 
 
-static void str_byte (void) {
+static void str_byte (lua_State *L) {
   long l;
-  const char *s = luaL_check_lstr(1, &l);
-  long pos = posrelat(luaL_opt_long(2, 1), l);
-  luaL_arg_check(0<pos && pos<=l, 2,  "out of range");
-  lua_pushnumber((unsigned char)s[pos-1]);
+  const char *s = luaL_check_lstr(L, 1, &l);
+  long pos = posrelat(luaL_opt_long(L, 2, 1), l);
+  luaL_arg_check(L, 0<pos && pos<=l, 2,  "out of range");
+  lua_pushnumber(L, (unsigned char)s[pos-1]);
 }
 
 
-static void str_char (void) {
+static void str_char (lua_State *L) {
   int i = 0;
-  luaL_resetbuffer();
-  while (lua_getparam(++i) != LUA_NOOBJECT) {
-    int c = luaL_check_int(i);
-    luaL_arg_check((unsigned char)c == c, i, "invalid value");
-    luaL_addchar((unsigned char)c);
+  luaL_resetbuffer(L);
+  while (lua_getparam(L, ++i) != LUA_NOOBJECT) {
+    int c = luaL_check_int(L, i);
+    luaL_arg_check(L, (unsigned char)c == c, i, "invalid value");
+    luaL_addchar(L, (unsigned char)c);
   }
-  closeandpush();
+  closeandpush(L);
 }
 
 
@@ -133,42 +135,42 @@ struct Capture {
 #define SPECIALS  "^$*+?.([%-"
 
 
-static void push_captures (struct Capture *cap) {
+static void push_captures (lua_State *L, struct Capture *cap) {
   int i;
   for (i=0; i<cap->level; i++) {
     int l = cap->capture[i].len;
-    if (l == -1) lua_error("unfinished capture");
-    lua_pushlstring(cap->capture[i].init, l);
+    if (l == -1) lua_error(L, "unfinished capture");
+    lua_pushlstring(L, cap->capture[i].init, l);
   }
 }
 
 
-static int check_cap (int l, struct Capture *cap) {
+static int check_cap (lua_State *L, int l, struct Capture *cap) {
   l -= '1';
   if (!(0 <= l && l < cap->level && cap->capture[l].len != -1))
-    lua_error("invalid capture index");
+    lua_error(L, "invalid capture index");
   return l;
 }
 
 
-static int capture_to_close (struct Capture *cap) {
+static int capture_to_close (lua_State *L, struct Capture *cap) {
   int level = cap->level;
   for (level--; level>=0; level--)
     if (cap->capture[level].len == -1) return level;
-  lua_error("invalid pattern capture");
+  lua_error(L, "invalid pattern capture");
   return 0;  /* to avoid warnings */
 }
 
 
-const char *luaI_classend (const char *p) {
+const char *luaI_classend (lua_State *L, const char *p) {
   switch (*p++) {
     case ESC:
-      if (*p == '\0') lua_error("incorrect pattern (ends with `%')");
+      if (*p == '\0') lua_error(L, "incorrect pattern (ends with `%')");
       return p+1;
     case '[':
       if (*p == '^') p++;
       do {  /* look for a ']' */
-        if (*p == '\0') lua_error("incorrect pattern (missing `]')");
+        if (*p == '\0') lua_error(L, "incorrect pattern (missing `]')");
         if (*(p++) == ESC && *p != '\0') p++;  /* skip escapes (e.g. '%]') */
       } while (*p != ']');
       return p+1;
@@ -236,13 +238,13 @@ int luaI_singlematch (int c, const char *p, const char *ep) {
 }
 
 
-static const char *match (const char *s, const char *p, struct Capture *cap);
+static const char *match (lua_State *L, const char *s, const char *p, struct Capture *cap);
 
 
-static const char *matchbalance (const char *s, const char *p,
+static const char *matchbalance (lua_State *L, const char *s, const char *p,
                                  struct Capture *cap) {
   if (*p == 0 || *(p+1) == 0)
-    lua_error("unbalanced pattern");
+    lua_error(L, "unbalanced pattern");
   if (*s != *p) return NULL;
   else {
     int b = *p;
@@ -259,14 +261,14 @@ static const char *matchbalance (const char *s, const char *p,
 }
 
 
-static const char *max_expand (const char *s, const char *p, const char *ep,
+static const char *max_expand (lua_State *L, const char *s, const char *p, const char *ep,
                          struct Capture *cap) {
   int i = 0;  /* counts maximum expand for item */
   while ((s+i)<cap->src_end && luaI_singlematch((unsigned char)*(s+i), p, ep))
     i++;
   /* keeps trying to match mith the maximum repetitions */
   while (i>=0) {
-    const char *res = match((s+i), ep+1, cap);
+    const char *res = match(L, (s+i), ep+1, cap);
     if (res) return res;
     i--;  /* else didn't match; reduce 1 repetition to try again */
   }
@@ -274,10 +276,10 @@ static const char *max_expand (const char *s, const char *p, const char *ep,
 }
 
 
-static const char *min_expand (const char *s, const char *p, const char *ep,
+static const char *min_expand (lua_State *L, const char *s, const char *p, const char *ep,
                          struct Capture *cap) {
   for (;;) {
-    const char *res = match(s, ep+1, cap);
+    const char *res = match(L, s, ep+1, cap);
     if (res != NULL)
       return res;
     else if (s<cap->src_end && luaI_singlematch((unsigned char)*s, p, ep))
@@ -287,34 +289,34 @@ static const char *min_expand (const char *s, const char *p, const char *ep,
 }
 
 
-static const char *start_capt (const char *s, const char *p,
+static const char *start_capt (lua_State *L, const char *s, const char *p,
                                struct Capture *cap) {
   const char *res;
   int level = cap->level;
-  if (level >= MAX_CAPT) lua_error("too many captures");
+  if (level >= MAX_CAPT) lua_error(L, "too many captures");
   cap->capture[level].init = s;
   cap->capture[level].len = -1;
   cap->level = level+1;
-  if ((res=match(s, p+1, cap)) == NULL)  /* match failed? */
+  if ((res=match(L, s, p+1, cap)) == NULL)  /* match failed? */
     cap->level--;  /* undo capture */
   return res;
 }
 
 
-static const char *end_capt (const char *s, const char *p,
+static const char *end_capt (lua_State *L, const char *s, const char *p,
                              struct Capture *cap) {
-  int l = capture_to_close(cap);
+  int l = capture_to_close(L, cap);
   const char *res;
   cap->capture[l].len = s - cap->capture[l].init;  /* close capture */
-  if ((res = match(s, p+1, cap)) == NULL)  /* match failed? */
+  if ((res = match(L, s, p+1, cap)) == NULL)  /* match failed? */
     cap->capture[l].len = -1;  /* undo capture */
   return res;
 }
 
 
-static const char *match_capture (const char *s, int level,
+static const char *match_capture (lua_State *L, const char *s, int level,
                                   struct Capture *cap) {
-  int l = check_cap(level, cap);
+  int l = check_cap(L, level, cap);
   int len = cap->capture[l].len;
   if (cap->src_end-s >= len &&
       memcmp(cap->capture[l].init, s, len) == 0)
@@ -323,23 +325,23 @@ static const char *match_capture (const char *s, int level,
 }
 
 
-static const char *match (const char *s, const char *p, struct Capture *cap) {
+static const char *match (lua_State *L, const char *s, const char *p, struct Capture *cap) {
   init: /* using goto's to optimize tail recursion */
   switch (*p) {
     case '(':  /* start capture */
-      return start_capt(s, p, cap);
+      return start_capt(L, s, p, cap);
     case ')':  /* end capture */
-      return end_capt(s, p, cap);
+      return end_capt(L, s, p, cap);
     case ESC:  /* may be %[0-9] or %b */
       if (isdigit((unsigned char)(*(p+1)))) {  /* capture? */
-        s = match_capture(s, *(p+1), cap);
+        s = match_capture(L, s, *(p+1), cap);
         if (s == NULL) return NULL;
-        p+=2; goto init;  /* else return match(s, p+2, cap) */
+        p+=2; goto init;  /* else return match(L, s, p+2, cap) */
       }
       else if (*(p+1) == 'b') {  /* balanced string? */
-        s = matchbalance(s, p+2, cap);
+        s = matchbalance(L, s, p+2, cap);
         if (s == NULL) return NULL;
-        p+=4; goto init;  /* else return match(s, p+4, cap); */
+        p+=4; goto init;  /* else return match(L, s, p+4, cap); */
       }
       else goto dflt;  /* case default */
     case '\0':  /* end of pattern */
@@ -349,24 +351,24 @@ static const char *match (const char *s, const char *p, struct Capture *cap) {
         return (s == cap->src_end) ? s : NULL;  /* check end of string */
       else goto dflt;
     default: dflt: {  /* it is a pattern item */
-      const char *ep = luaI_classend(p);  /* points to what is next */
+      const char *ep = luaI_classend(L, p);  /* points to what is next */
       int m = s<cap->src_end && luaI_singlematch((unsigned char)*s, p, ep);
       switch (*ep) {
         case '?': {  /* optional */
           const char *res;
-          if (m && ((res=match(s+1, ep+1, cap)) != NULL))
+          if (m && ((res=match(L, s+1, ep+1, cap)) != NULL))
             return res;
-          p=ep+1; goto init;  /* else return match(s, ep+1, cap); */
+          p=ep+1; goto init;  /* else return match(L, s, ep+1, cap); */
         }
         case '*':  /* 0 or more repetitions */
-          return max_expand(s, p, ep, cap);
+          return max_expand(L, s, p, ep, cap);
         case '+':  /* 1 or more repetitions */
-          return (m ? max_expand(s+1, p, ep, cap) : NULL);
+          return (m ? max_expand(L, s+1, p, ep, cap) : NULL);
         case '-':  /* 0 or more repetitions (minimum) */
-          return min_expand(s, p, ep, cap);
+          return min_expand(L, s, p, ep, cap);
         default:
           if (!m) return NULL;
-          s++; p=ep; goto init;  /* else return match(s+1, ep, cap); */
+          s++; p=ep; goto init;  /* else return match(L, s+1, ep, cap); */
       }
     }
   }
@@ -394,19 +396,19 @@ static const char *memfind (const char *s1, long l1, const char *s2, long l2) {
 }
 
 
-static void str_find (void) {
+static void str_find (lua_State *L) {
   long l1, l2;
-  const char *s = luaL_check_lstr(1, &l1);
-  const char *p = luaL_check_lstr(2, &l2);
-  long init = posrelat(luaL_opt_long(3, 1), l1) - 1;
+  const char *s = luaL_check_lstr(L, 1, &l1);
+  const char *p = luaL_check_lstr(L, 2, &l2);
+  long init = posrelat(luaL_opt_long(L, 3, 1), l1) - 1;
   struct Capture cap;
-  luaL_arg_check(0 <= init && init <= l1, 3, "out of range");
-  if (lua_getparam(4) != LUA_NOOBJECT ||
+  luaL_arg_check(L, 0 <= init && init <= l1, 3, "out of range");
+  if (lua_getparam(L, 4) != LUA_NOOBJECT ||
       strpbrk(p, SPECIALS) == NULL) {  /* no special characters? */
     const char *s2 = memfind(s+init, l1, p, l2);
     if (s2) {
-      lua_pushnumber(s2-s+1);
-      lua_pushnumber(s2-s+l2);
+      lua_pushnumber(L, s2-s+1);
+      lua_pushnumber(L, s2-s+l2);
       return;
     }
   }
@@ -417,33 +419,33 @@ static void str_find (void) {
     do {
       const char *res;
       cap.level = 0;
-      if ((res=match(s1, p, &cap)) != NULL) {
-        lua_pushnumber(s1-s+1);  /* start */
-        lua_pushnumber(res-s);   /* end */
-        push_captures(&cap);
+      if ((res=match(L, s1, p, &cap)) != NULL) {
+        lua_pushnumber(L, s1-s+1);  /* start */
+        lua_pushnumber(L, res-s);   /* end */
+        push_captures(L, &cap);
         return;
       }
     } while (s1++<cap.src_end && !anchor);
   }
-  lua_pushnil();  /* not found */
+  lua_pushnil(L);  /* not found */
 }
 
 
-static void add_s (lua_Object newp, struct Capture *cap) {
-  if (lua_isstring(newp)) {
-    const char *news = lua_getstring(newp);
-    int l = lua_strlen(newp);
+static void add_s (lua_State *L, lua_Object newp, struct Capture *cap) {
+  if (lua_isstring(L, newp)) {
+    const char *news = lua_getstring(L, newp);
+    int l = lua_strlen(L, newp);
     int i;
     for (i=0; i<l; i++) {
       if (news[i] != ESC)
-        luaL_addchar(news[i]);
+        luaL_addchar(L, news[i]);
       else {
         i++;  /* skip ESC */
         if (!isdigit((unsigned char)news[i]))
-          luaL_addchar(news[i]);
+          luaL_addchar(L, news[i]);
         else {
-          int level = check_cap(news[i], cap);
-          addnchar(cap->capture[level].init, cap->capture[level].len);
+          int level = check_cap(L, news[i], cap);
+          addnchar(L, cap->capture[level].init, cap->capture[level].len);
         }
       }
     }
@@ -452,91 +454,91 @@ static void add_s (lua_Object newp, struct Capture *cap) {
     lua_Object res;
     int status;
     int oldbuff;
-    lua_beginblock();
-    push_captures(cap);
+    lua_beginblock(L);
+    push_captures(L, cap);
     /* function may use buffer, so save it and create a new one */
-    oldbuff = luaL_newbuffer(0);
-    status = lua_callfunction(newp);
+    oldbuff = luaL_newbuffer(L, 0);
+    status = lua_callfunction(L, newp);
     /* restore old buffer */
-    luaL_oldbuffer(oldbuff);
+    luaL_oldbuffer(L, oldbuff);
     if (status != 0) {
-      lua_endblock();
-      lua_error(NULL);
+      lua_endblock(L);
+      lua_error(L, NULL);
     }
-    res = lua_getresult(1);
-    if (lua_isstring(res))
-      addnchar(lua_getstring(res), lua_strlen(res));
-    lua_endblock();
+    res = lua_getresult(L, 1);
+    if (lua_isstring(L, res))
+      addnchar(L, lua_getstring(L, res), lua_strlen(L, res));
+    lua_endblock(L);
   }
 }
 
 
-static void str_gsub (void) {
+static void str_gsub (lua_State *L) {
   long srcl;
-  const char *src = luaL_check_lstr(1, &srcl);
-  const char *p = luaL_check_string(2);
-  lua_Object newp = lua_getparam(3);
-  int max_s = luaL_opt_int(4, srcl+1);
+  const char *src = luaL_check_lstr(L, 1, &srcl);
+  const char *p = luaL_check_string(L, 2);
+  lua_Object newp = lua_getparam(L, 3);
+  int max_s = luaL_opt_int(L, 4, srcl+1);
   int anchor = (*p == '^') ? (p++, 1) : 0;
   int n = 0;
   struct Capture cap;
-  luaL_arg_check(lua_isstring(newp) || lua_isfunction(newp), 3,
+  luaL_arg_check(L, lua_isstring(L, newp) || lua_isfunction(L, newp), 3,
                  "string or function expected");
-  luaL_resetbuffer();
+  luaL_resetbuffer(L);
   cap.src_end = src+srcl;
   while (n < max_s) {
     const char *e;
     cap.level = 0;
-    e = match(src, p, &cap);
+    e = match(L, src, p, &cap);
     if (e) {
       n++;
-      add_s(newp, &cap);
+      add_s(L, newp, &cap);
     }
     if (e && e>src) /* non empty match? */
       src = e;  /* skip it */
     else if (src < cap.src_end)
-      luaL_addchar(*src++);
+      luaL_addchar(L, *src++);
     else break;
     if (anchor) break;
   }
-  addnchar(src, cap.src_end-src);
-  closeandpush();
-  lua_pushnumber(n);  /* number of substitutions */
+  addnchar(L, src, cap.src_end-src);
+  closeandpush(L);
+  lua_pushnumber(L, n);  /* number of substitutions */
 }
 
 /* }====================================================== */
 
 
-static void luaI_addquoted (int arg) {
+static void luaI_addquoted (lua_State *L, int arg) {
   long l;
-  const char *s = luaL_check_lstr(arg, &l);
-  luaL_addchar('"');
+  const char *s = luaL_check_lstr(L, arg, &l);
+  luaL_addchar(L, '"');
   while (l--) {
     switch (*s) {
       case '"':  case '\\':  case '\n':
-        luaL_addchar('\\');
-        luaL_addchar(*s);
+        luaL_addchar(L, '\\');
+        luaL_addchar(L, *s);
         break;
-      case '\0': addnchar("\\000", 4); break;
-      default: luaL_addchar(*s);
+      case '\0': addnchar(L, "\\000", 4); break;
+      default: luaL_addchar(L, *s);
     }
     s++;
   }
-  luaL_addchar('"');
+  luaL_addchar(L, '"');
 }
 
 /* maximum size of each format specification (such as '%-099.99d') */
 #define MAX_FORMAT 20  /* arbitrary limit */
 
-static void str_format (void) {
+static void str_format (lua_State *L) {
   int arg = 1;
-  const char *strfrmt = luaL_check_string(arg);
-  luaL_resetbuffer();
+  const char *strfrmt = luaL_check_string(L, arg);
+  luaL_resetbuffer(L);
   while (*strfrmt) {
     if (*strfrmt != '%')
-      luaL_addchar(*strfrmt++);
+      luaL_addchar(L, *strfrmt++);
     else if (*++strfrmt == '%')
-      luaL_addchar(*strfrmt++);  /* %% */
+      luaL_addchar(L, *strfrmt++);  /* %% */
     else { /* format item */
       struct Capture cap;
       char form[MAX_FORMAT];  /* to store the format ('%...') */
@@ -550,33 +552,33 @@ static void str_format (void) {
       arg++;
       cap.src_end = strfrmt+strlen(strfrmt)+1;
       cap.level = 0;
-      strfrmt = match(initf, "[-+ #0]*(%d*)%.?(%d*)", &cap);
+      strfrmt = match(L, initf, "[-+ #0]*(%d*)%.?(%d*)", &cap);
       if (cap.capture[0].len > 2 || cap.capture[1].len > 2 ||  /* < 100? */
           strfrmt-initf > MAX_FORMAT-2)
-        lua_error("invalid format (width or precision too long)");
+        lua_error(L, "invalid format (width or precision too long)");
       strncpy(form+1, initf, strfrmt-initf+1); /* +1 to include conversion */
       form[strfrmt-initf+2] = 0;
-      buff = luaL_openspace(512);  /* 512 > soid luaI_addquot99.99f', -1e308) */
+      buff = luaL_openspace(L, 512);  /* 512 > len(format('%99.99f', -1e308)) */
       switch (*strfrmt++) {
         case 'c':  case 'd':  case 'i':
-          sprintf(buff, form, luaL_check_int(arg));
+          sprintf(buff, form, luaL_check_int(L, arg));
           break;
         case 'o':  case 'u':  case 'x':  case 'X':
-          sprintf(buff, form, (unsigned int)luaL_check_number(arg));
+          sprintf(buff, form, (unsigned int)luaL_check_number(L, arg));
           break;
         case 'e':  case 'E': case 'f': case 'g': case 'G':
-          sprintf(buff, form, luaL_check_number(arg));
+          sprintf(buff, form, luaL_check_number(L, arg));
           break;
         case 'q':
-          luaI_addquoted(arg);
+          luaI_addquoted(L, arg);
           continue;  /* skip the "addsize" at the end */
         case 's': {
           long l;
-          const char *s = luaL_check_lstr(arg, &l);
+          const char *s = luaL_check_lstr(L, arg, &l);
           if (cap.capture[1].len == 0 && l >= 100) {
             /* no precision and string is too big to be formatted;
                keep original string */
-            addnchar(s, l);
+            addnchar(L, s, l);
             continue;  /* skip the "addsize" at the end */
           }
           else {
@@ -585,12 +587,12 @@ static void str_format (void) {
           }
         }
         default:  /* also treat cases 'pnLlh' */
-          lua_error("invalid option in `format'");
+          lua_error(L, "invalid option in `format'");
       }
-      luaL_addsize(strlen(buff));
+      luaL_addsize(L, strlen(buff));
     }
   }
-  closeandpush();  /* push the result */
+  closeandpush(L);  /* push the result */
 }
 
 
@@ -612,7 +614,7 @@ static const struct luaL_reg strlib[] = {
 /*
 ** Open string library
 */
-void strlib_open (void)
+void lua_strlibopen (lua_State *L)
 {
-  luaL_openlib(strlib, (sizeof(strlib)/sizeof(strlib[0])));
+  luaL_openlib(L, strlib, (sizeof(strlib)/sizeof(strlib[0])));
 }

+ 41 - 39
ltable.c

@@ -1,5 +1,5 @@
 /*
-** $Id: ltable.c,v 1.28 1999/10/26 10:53:40 roberto Exp roberto $
+** $Id: ltable.c,v 1.29 1999/11/10 15:39:35 roberto Exp roberto $
 ** Lua tables (hash)
 ** See Copyright Notice in lua.h
 */
@@ -18,6 +18,8 @@
 */
 
 
+#define LUA_REENTRANT
+
 #include "lauxlib.h"
 #include "lmem.h"
 #include "lobject.h"
@@ -26,7 +28,7 @@
 #include "lua.h"
 
 
-#define gcsize(n)	numblocks(n*2, sizeof(Hash))
+#define gcsize(L, n)	numblocks(L, n*2, sizeof(Hash))
 
 
 
@@ -38,7 +40,7 @@
 ** returns the `main' position of an element in a table (that is, the index
 ** of its hash value)
 */
-Node *luaH_mainposition (const Hash *t, const TObject *key) {
+Node *luaH_mainposition (lua_State *L, const Hash *t, const TObject *key) {
   unsigned long h;
   switch (ttype(key)) {
     case LUA_T_NUMBER:
@@ -48,27 +50,27 @@ Node *luaH_mainposition (const Hash *t, const TObject *key) {
       h = tsvalue(key)->hash;
       break;
     case LUA_T_ARRAY:
-      h = IntPoint(avalue(key));
+      h = IntPoint(L, avalue(key));
       break;
     case LUA_T_PROTO:
-      h = IntPoint(tfvalue(key));
+      h = IntPoint(L, tfvalue(key));
       break;
     case LUA_T_CPROTO:
-      h = IntPoint(fvalue(key));
+      h = IntPoint(L, fvalue(key));
       break;
     case LUA_T_CLOSURE:
-      h = IntPoint(clvalue(key));
+      h = IntPoint(L, clvalue(key));
       break;
     default:
-      lua_error("unexpected type to index table");
+      lua_error(L, "unexpected type to index table");
       h = 0;  /* to avoid warnings */
   }
   return &t->node[h%(unsigned int)t->size];
 }
 
 
-const TObject *luaH_get (const Hash *t, const TObject *key) {
-  Node *n = luaH_mainposition(t, key);
+const TObject *luaH_get (lua_State *L, const Hash *t, const TObject *key) {
+  Node *n = luaH_mainposition(L, t, key);
   do {
     if (luaO_equalObj(key, &n->key))
       return &n->val;
@@ -78,16 +80,16 @@ const TObject *luaH_get (const Hash *t, const TObject *key) {
 }
 
 
-int luaH_pos (const Hash *t, const TObject *key) {
-  const TObject *v = luaH_get(t, key);
+int luaH_pos (lua_State *L, const Hash *t, const TObject *key) {
+  const TObject *v = luaH_get(L, t, key);
   return (v == &luaO_nilobject) ?  -1 :  /* key not found */
              ((const char *)v - (const char *)(&t->node[0].val))/sizeof(Node);
 }
 
 
 
-static Node *hashnodecreate (int nhash) {
-  Node *v = luaM_newvector(nhash, Node);
+static Node *hashnodecreate (lua_State *L, int nhash) {
+  Node *v = luaM_newvector(L, nhash, Node);
   int i;
   for (i=0; i<nhash; i++) {
     ttype(&v[i].key) = ttype(&v[i].val) = LUA_T_NIL;
@@ -97,17 +99,17 @@ static Node *hashnodecreate (int nhash) {
 }
 
 
-static void setnodevector (Hash *t, int size) {
-  t->node = hashnodecreate(size);
+static void setnodevector (lua_State *L, Hash *t, int size) {
+  t->node = hashnodecreate(L, size);
   t->size = size;
   t->firstfree = &t->node[size-1];  /* first free position to be used */
-  L->nblocks += gcsize(size);
+  L->nblocks += gcsize(L, size);
 }
 
 
-Hash *luaH_new (int size) {
-  Hash *t = luaM_new(Hash);
-  setnodevector(t, luaO_redimension(size+1));
+Hash *luaH_new (lua_State *L, int size) {
+  Hash *t = luaM_new(L, Hash);
+  setnodevector(L, t, luaO_redimension(L, size+1));
   t->htag = TagDefault;
   t->next = L->roottable;
   L->roottable = t;
@@ -116,14 +118,14 @@ Hash *luaH_new (int size) {
 }
 
 
-void luaH_free (Hash *t) {
-  L->nblocks -= gcsize(t->size);
-  luaM_free(t->node);
-  luaM_free(t);
+void luaH_free (lua_State *L, Hash *t) {
+  L->nblocks -= gcsize(L, t->size);
+  luaM_free(L, t->node);
+  luaM_free(L, t);
 }
 
 
-static int newsize (const Hash *t) {
+static int newsize (lua_State *L, const Hash *t) {
   Node *v = t->node;
   int size = t->size;
   int realuse = 0;
@@ -132,7 +134,7 @@ static int newsize (const Hash *t) {
     if (ttype(&v[i].val) != LUA_T_NIL)
       realuse++;
   }
-  return luaO_redimension(realuse*2);
+  return luaO_redimension(L, realuse*2);
 }
 
 
@@ -141,19 +143,19 @@ static int newsize (const Hash *t) {
 ** main position is free, to avoid needless collisions. In the second stage,
 ** we insert the other elements.
 */
-static void rehash (Hash *t) {
+static void rehash (lua_State *L, Hash *t) {
   int oldsize = t->size;
   Node *nold = t->node;
   int i;
-  L->nblocks -= gcsize(oldsize);
-  setnodevector(t, newsize(t));  /* create new array of nodes */
+  L->nblocks -= gcsize(L, oldsize);
+  setnodevector(L, t, newsize(L, t));  /* create new array of nodes */
   /* first loop; set only elements that can go in their main positions */
   for (i=0; i<oldsize; i++) {
     Node *old = nold+i;
     if (ttype(&old->val) == LUA_T_NIL)
       old->next = NULL;  /* `remove' it for next loop */
     else {
-      Node *mp = luaH_mainposition(t, &old->key);  /* new main position */
+      Node *mp = luaH_mainposition(L, t, &old->key);  /* new main position */
       if (ttype(&mp->key) == LUA_T_NIL) {  /* is it empty? */
         mp->key = old->key;  /* put element there */
         mp->val = old->val;
@@ -180,7 +182,7 @@ static void rehash (Hash *t) {
       } while (ttype(&t->firstfree->key) != LUA_T_NIL);
     }
   }
-  luaM_free(nold);  /* free old array */
+  luaM_free(L, nold);  /* free old array */
 }
 
 
@@ -197,8 +199,8 @@ static void rehash (Hash *t) {
 ** pair; therefore, even when `val' points to an element of this table
 ** (this happens when we use `luaH_move'), there is no problem.
 */
-void luaH_set (Hash *t, const TObject *key, const TObject *val) {
-  Node *mp = luaH_mainposition(t, key);
+void luaH_set (lua_State *L, Hash *t, const TObject *key, const TObject *val) {
+  Node *mp = luaH_mainposition(L, t, key);
   Node *n = mp;
   do {  /* check whether `key' is somewhere in the chain */
     if (luaO_equalObj(key, &n->key)) {
@@ -213,7 +215,7 @@ void luaH_set (Hash *t, const TObject *key, const TObject *val) {
     n = t->firstfree;  /* get a free place */
     /* is colliding node out of its main position? (can only happens if
        its position if after "firstfree") */
-    if (mp > n && (othern=luaH_mainposition(t, &mp->key)) != mp) {
+    if (mp > n && (othern=luaH_mainposition(L, t, &mp->key)) != mp) {
       /* yes; move colliding node into free position */
       while (othern->next != mp) othern = othern->next;  /* find previous */
       othern->next = n;  /* redo the chain with `n' in place of `mp' */
@@ -235,22 +237,22 @@ void luaH_set (Hash *t, const TObject *key, const TObject *val) {
     else if (t->firstfree == t->node) break;  /* cannot decrement from here */
     else (t->firstfree)--;
   }
-  rehash(t);  /* no more free places */
+  rehash(L, t);  /* no more free places */
 }
 
 
-void luaH_setint (Hash *t, int key, const TObject *val) {
+void luaH_setint (lua_State *L, Hash *t, int key, const TObject *val) {
   TObject index;
   ttype(&index) = LUA_T_NUMBER;
   nvalue(&index) = key;
-  luaH_set(t, &index, val);
+  luaH_set(L, t, &index, val);
 }
 
 
-const TObject *luaH_getint (const Hash *t, int key) {
+const TObject *luaH_getint (lua_State *L, const Hash *t, int key) {
   TObject index;
   ttype(&index) = LUA_T_NUMBER;
   nvalue(&index) = key;
-  return luaH_get(t, &index);
+  return luaH_get(L, t, &index);
 }
 

+ 14 - 14
ltable.h

@@ -1,5 +1,5 @@
 /*
-** $Id: ltable.h,v 1.14 1999/10/14 19:13:31 roberto Exp roberto $
+** $Id: ltable.h,v 1.15 1999/10/26 10:53:40 roberto Exp roberto $
 ** Lua tables (hash)
 ** See Copyright Notice in lua.h
 */
@@ -10,23 +10,23 @@
 #include "lobject.h"
 
 
-#define node(t,i)       (&(t)->node[i])
-#define key(n)		(&(n)->key)
-#define val(n)		(&(n)->val)
+#define node(L, t,i)       (&(t)->node[i])
+#define key(L, n)		(&(n)->key)
+#define val(L, n)		(&(n)->val)
 
-#define luaH_move(t,from,to)	(luaH_setint(t, to, luaH_getint(t, from)))
+#define luaH_move(L, t,from,to)	(luaH_setint(L, t, to, luaH_getint(L, t, from)))
 
-Hash *luaH_new (int nhash);
-void luaH_free (Hash *t);
-const TObject *luaH_get (const Hash *t, const TObject *key);
-void luaH_set (Hash *t, const TObject *key, const TObject *val);
-int luaH_pos (const Hash *t, const TObject *r);
-void luaH_setint (Hash *t, int key, const TObject *val);
-const TObject *luaH_getint (const Hash *t, int key);
-unsigned long luaH_hash (const TObject *key);
+Hash *luaH_new (lua_State *L, int nhash);
+void luaH_free (lua_State *L, Hash *t);
+const TObject *luaH_get (lua_State *L, const Hash *t, const TObject *key);
+void luaH_set (lua_State *L, Hash *t, const TObject *key, const TObject *val);
+int luaH_pos (lua_State *L, const Hash *t, const TObject *r);
+void luaH_setint (lua_State *L, Hash *t, int key, const TObject *val);
+const TObject *luaH_getint (lua_State *L, const Hash *t, int key);
+unsigned long luaH_hash (lua_State *L, const TObject *key);
 
 /* exported only for debugging */
-Node *luaH_mainposition (const Hash *t, const TObject *key);
+Node *luaH_mainposition (lua_State *L, const Hash *t, const TObject *key);
 
 
 #endif

+ 34 - 32
ltm.c

@@ -1,5 +1,5 @@
 /*
-** $Id: ltm.c,v 1.27 1999/09/20 14:57:29 roberto Exp roberto $
+** $Id: ltm.c,v 1.28 1999/10/04 17:51:04 roberto Exp roberto $
 ** Tag methods
 ** See Copyright Notice in lua.h
 */
@@ -8,6 +8,8 @@
 #include <stdio.h>
 #include <string.h>
 
+#define LUA_REENTRANT
+
 #include "lauxlib.h"
 #include "lmem.h"
 #include "lobject.h"
@@ -22,10 +24,10 @@ const char *const luaT_eventname[] = {  /* ORDER IM */
 };
 
 
-static int luaI_checkevent (const char *name, const char *const list[]) {
+static int luaI_checkevent (lua_State *L, const char *name, const char *const list[]) {
   int e = luaL_findstring(name, list);
   if (e < 0)
-    luaL_verror("`%.50s' is not a valid event name", name);
+    luaL_verror(L, "`%.50s' is not a valid event name", name);
   return e;
 }
 
@@ -54,48 +56,48 @@ int luaT_validevent (int t, int e) {  /* ORDER LUA_T */
 }
 
 
-static void init_entry (int tag) {
+static void init_entry (lua_State *L, int tag) {
   int i;
   for (i=0; i<IM_N; i++)
-    ttype(luaT_getim(tag, i)) = LUA_T_NIL;
+    ttype(luaT_getim(L, tag, i)) = LUA_T_NIL;
 }
 
 
-void luaT_init (void) {
+void luaT_init (lua_State *L) {
   int t;
   L->last_tag = -(NUM_TAGS-1);
-  luaM_growvector(L->IMtable, 0, NUM_TAGS, struct IM, arrEM, MAX_INT);
+  luaM_growvector(L, L->IMtable, 0, NUM_TAGS, struct IM, arrEM, MAX_INT);
   for (t=L->last_tag; t<=0; t++)
-    init_entry(t);
+    init_entry(L, t);
 }
 
 
-int lua_newtag (void) {
+int lua_newtag (lua_State *L) {
   --L->last_tag;
-  luaM_growvector(L->IMtable, -(L->last_tag), 1, struct IM, arrEM, MAX_INT);
-  init_entry(L->last_tag);
+  luaM_growvector(L, L->IMtable, -(L->last_tag), 1, struct IM, arrEM, MAX_INT);
+  init_entry(L, L->last_tag);
   return L->last_tag;
 }
 
 
-static void checktag (int tag) {
+static void checktag (lua_State *L, int tag) {
   if (!(L->last_tag <= tag && tag <= 0))
-    luaL_verror("%d is not a valid tag", tag);
+    luaL_verror(L, "%d is not a valid tag", tag);
 }
 
-void luaT_realtag (int tag) {
+void luaT_realtag (lua_State *L, int tag) {
   if (!(L->last_tag <= tag && tag < LUA_T_NIL))
-    luaL_verror("tag %d was not created by `newtag'", tag);
+    luaL_verror(L, "tag %d was not created by `newtag'", tag);
 }
 
 
-int lua_copytagmethods (int tagto, int tagfrom) {
+int lua_copytagmethods (lua_State *L, int tagto, int tagfrom) {
   int e;
-  checktag(tagto);
-  checktag(tagfrom);
+  checktag(L, tagto);
+  checktag(L, tagfrom);
   for (e=0; e<IM_N; e++) {
     if (luaT_validevent(tagto, e))
-      *luaT_getim(tagto, e) = *luaT_getim(tagfrom, e);
+      *luaT_getim(L, tagto, e) = *luaT_getim(L, tagfrom, e);
   }
   return tagto;
 }
@@ -115,7 +117,7 @@ int luaT_effectivetag (const TObject *o) {
 #ifdef DEBUG
     case LUA_T_PMARK: case LUA_T_CMARK:
     case LUA_T_CLMARK: case LUA_T_LINE:
-      LUA_INTERNALERROR("invalid type");
+      LUA_INTERNALERROR(L, "invalid type");
 #endif
     default:
       return t;
@@ -123,37 +125,37 @@ int luaT_effectivetag (const TObject *o) {
 }
 
 
-const TObject *luaT_gettagmethod (int t, const char *event) {
-  int e = luaI_checkevent(event, luaT_eventname);
-  checktag(t);
+const TObject *luaT_gettagmethod (lua_State *L, int t, const char *event) {
+  int e = luaI_checkevent(L, event, luaT_eventname);
+  checktag(L, t);
   if (luaT_validevent(t, e))
-    return luaT_getim(t,e);
+    return luaT_getim(L, t,e);
   else
     return &luaO_nilobject;
 }
 
 
-void luaT_settagmethod (int t, const char *event, TObject *func) {
+void luaT_settagmethod (lua_State *L, int t, const char *event, TObject *func) {
   TObject temp;
-  int e = luaI_checkevent(event, luaT_eventname);
-  checktag(t);
+  int e = luaI_checkevent(L, event, luaT_eventname);
+  checktag(L, t);
   if (!luaT_validevent(t, e))
-    luaL_verror("cannot change tag method `%.20s' for type `%.20s'%.20s",
+    luaL_verror(L, "cannot change tag method `%.20s' for type `%.20s'%.20s",
                 luaT_eventname[e], luaO_typenames[-t],
                 (t == LUA_T_ARRAY || t == LUA_T_USERDATA) ? " with default tag"
                                                           : "");
   temp = *func;
-  *func = *luaT_getim(t,e);
-  *luaT_getim(t, e) = temp;
+  *func = *luaT_getim(L, t,e);
+  *luaT_getim(L, t, e) = temp;
 }
 
 
-const char *luaT_travtagmethods (int (*fn)(TObject *)) {  /* ORDER IM */
+const char *luaT_travtagmethods (lua_State *L, int (*fn)(lua_State *, TObject *)) {  /* ORDER IM */
   int e;
   for (e=IM_GETTABLE; e<=IM_FUNCTION; e++) {
     int t;
     for (t=0; t>=L->last_tag; t--)
-      if (fn(luaT_getim(t,e)))
+      if (fn(L, luaT_getim(L, t,e)))
         return luaT_eventname[e];
   }
   return NULL;

+ 8 - 8
ltm.h

@@ -1,5 +1,5 @@
 /*
-** $Id: ltm.h,v 1.6 1999/08/16 20:52:00 roberto Exp roberto $
+** $Id: ltm.h,v 1.7 1999/09/20 14:57:29 roberto Exp roberto $
 ** Tag methods
 ** See Copyright Notice in lua.h
 */
@@ -44,18 +44,18 @@ struct IM {
 };
 
 
-#define luaT_getim(tag,event) (&L->IMtable[-(tag)].int_method[event])
-#define luaT_getimbyObj(o,e)  (luaT_getim(luaT_effectivetag(o),(e)))
+#define luaT_getim(L,tag,event) (&L->IMtable[-(tag)].int_method[event])
+#define luaT_getimbyObj(L,o,e)  (luaT_getim(L, luaT_effectivetag(o),(e)))
 
 extern const char *const luaT_eventname[];
 
 
-void luaT_init (void);
-void luaT_realtag (int tag);
+void luaT_init (lua_State *L);
+void luaT_realtag (lua_State *L, int tag);
 int luaT_effectivetag (const TObject *o);
-void luaT_settagmethod (int t, const char *event, TObject *func);
-const TObject *luaT_gettagmethod (int t, const char *event);
-const char *luaT_travtagmethods (int (*fn)(TObject *));
+void luaT_settagmethod (lua_State *L, int t, const char *event, TObject *func);
+const TObject *luaT_gettagmethod (lua_State *L, int t, const char *event);
+const char *luaT_travtagmethods (lua_State *L, int (*fn)(lua_State *, TObject *));
 
 int luaT_validevent (int t, int e);
 

+ 8 - 9
lua.c

@@ -1,5 +1,5 @@
 /*
-** $Id: lua.c,v 1.25 1999/11/12 13:54:44 roberto Exp roberto $
+** $Id: lua.c,v 1.26 1999/11/16 12:50:48 roberto Exp roberto $
 ** Lua stand-alone interpreter
 ** See Copyright Notice in lua.h
 */
@@ -21,7 +21,6 @@
 static int isatty (int x) { return x==0; }  /* assume stdin is a tty */
 #endif
 
-
 typedef void (*handler)(int);  /* type for signal actions */
 
 static void laction (int i);
@@ -37,8 +36,8 @@ static handler lreset (void) {
 
 
 static void lstop (void) {
-  lua_setlinehook(old_linehook);
-  lua_setcallhook(old_callhook);
+  lua_setlinehook(lua_state, old_linehook);
+  lua_setcallhook(lua_state, old_callhook);
   lreset();
   lua_error("interrupted!");
 }
@@ -48,15 +47,15 @@ static void laction (int i) {
   (void)i;  /* to avoid warnings */
   signal(SIGINT, SIG_DFL); /* if another SIGINT happens before lstop,
                               terminate process (default action) */
-  old_linehook = lua_setlinehook((lua_LHFunction)lstop);
-  old_callhook = lua_setcallhook((lua_CHFunction)lstop);
+  old_linehook = lua_setlinehook(lua_state, (lua_LHFunction)lstop);
+  old_callhook = lua_setcallhook(lua_state, (lua_CHFunction)lstop);
 }
 
 
-static int ldo (int (*f)(const char *), const char *name) {
+static int ldo (int (*f)(lua_State *L, const char *), const char *name) {
   int res;
   handler h = lreset();
-  res = f(name);  /* dostring | dofile */
+  res = f(lua_state, name);  /* dostring | dofile */
   signal(SIGINT, h);  /* restore old action */
   return res;
 }
@@ -172,7 +171,7 @@ int main (int argc, char *argv[]) {
           manual_input(0);
           break;
         case 'd':
-          lua_setdebug(1);
+          lua_setdebug(lua_state, 1);
           break;
         case 'v':
           printf("%s  %s\n(written by %s)\n",

+ 145 - 90
lua.h

@@ -1,5 +1,5 @@
 /*
-** $Id: lua.h,v 1.36 1999/10/07 19:04:30 roberto Exp roberto $
+** $Id: lua.h,v 1.37 1999/11/11 17:02:40 roberto Exp roberto $
 ** Lua - An Extensible Extension Language
 ** TeCGraf: Grupo de Tecnologia em Computacao Grafica, PUC-Rio, Brazil
 ** e-mail: [email protected]
@@ -21,144 +21,199 @@
 #define LUA_NOREF	(-2)
 #define LUA_REFNIL	(-1)
 
-#define LUA_ANYTAG    (-1)
+#define LUA_ANYTAG	(-1)
 
 typedef struct lua_State lua_State;
-extern lua_State *lua_state;
 
-typedef void (*lua_CFunction) (void);
+typedef void (*lua_CFunction) ();
 typedef unsigned int lua_Object;
 
-void	       lua_open			(void);
-void           lua_close		(void);
-lua_State      *lua_setstate		(lua_State *st);
+lua_State     *lua_newstate (void);
+void           lua_close (lua_State *L);
 
-lua_Object     lua_settagmethod	(int tag, const char *event);
+lua_Object     lua_settagmethod (lua_State *L, int tag, const char *event);
                                                        /* In: new method */
-lua_Object     lua_gettagmethod	(int tag, const char *event);
+lua_Object     lua_gettagmethod (lua_State *L, int tag, const char *event);
 
-int            lua_newtag		(void);
-int            lua_copytagmethods	(int tagto, int tagfrom);
-void           lua_settag		(int tag); /* In: object */
+int            lua_newtag (lua_State *L);
+int            lua_copytagmethods (lua_State *L, int tagto, int tagfrom);
+void           lua_settag (lua_State *L, int tag); /* In: object */
 
-void           lua_error		(const char *s);
-int            lua_dofile 		(const char *filename);
+void           lua_error (lua_State *L, const char *s);
+int            lua_dofile (lua_State *L, const char *filename);
                                                         /* Out: returns */
-int            lua_dostring 		(const char *string);
+int            lua_dostring (lua_State *L, const char *string);
                                                         /* Out: returns */
-int            lua_dobuffer		(const char *buff, int size,
+int            lua_dobuffer (lua_State *L, const char *buff, int size,
                                          const char *name); /* Out: returns */
-int            lua_callfunction		(lua_Object f);
+int            lua_callfunction (lua_State *L, lua_Object f);
 					  /* In: parameters; Out: returns */
 
-void	       lua_beginblock		(void);
-void	       lua_endblock		(void);
+void	       lua_beginblock (lua_State *L);
+void	       lua_endblock (lua_State *L);
 
-lua_Object     lua_lua2C 		(int number);
-#define	       lua_getparam(_)		lua_lua2C(_)
-#define	       lua_getresult(_)		lua_lua2C(_)
+lua_Object     lua_lua2C (lua_State *L, int number);
+#define	       lua_getparam		lua_lua2C
+#define	       lua_getresult		lua_lua2C
 
-const char    *lua_type			(lua_Object object);
+const char    *lua_type (lua_State *L, lua_Object object);
 
-int            lua_isnil                (lua_Object object);
-int            lua_istable              (lua_Object object);
-int            lua_isuserdata           (lua_Object object);
-int            lua_iscfunction          (lua_Object object);
-int            lua_isnumber             (lua_Object object);
-int            lua_isstring             (lua_Object object);
-int            lua_isfunction           (lua_Object object);
+int            lua_isnil (lua_State *L, lua_Object object);
+int            lua_istable (lua_State *L, lua_Object object);
+int            lua_isuserdata (lua_State *L, lua_Object object);
+int            lua_iscfunction (lua_State *L, lua_Object object);
+int            lua_isnumber (lua_State *L, lua_Object object);
+int            lua_isstring (lua_State *L, lua_Object object);
+int            lua_isfunction (lua_State *L, lua_Object object);
 
-int            lua_equalobj		(lua_Object o1, lua_Object o2);
+int            lua_equalobj (lua_State *L, lua_Object o1, lua_Object o2);
 
-double         lua_getnumber 		(lua_Object object);
-const char    *lua_getstring 		(lua_Object object);
-long           lua_strlen 		(lua_Object object);
-lua_CFunction  lua_getcfunction 	(lua_Object object);
-void	      *lua_getuserdata		(lua_Object object);
+double         lua_getnumber (lua_State *L, lua_Object object);
+const char    *lua_getstring (lua_State *L, lua_Object object);
+long           lua_strlen (lua_State *L, lua_Object object);
+lua_CFunction  lua_getcfunction (lua_State *L, lua_Object object);
+void	      *lua_getuserdata (lua_State *L, lua_Object object);
 
 
-void 	       lua_pushnil 		(void);
-void           lua_pushnumber 		(double n);
-void           lua_pushlstring		(const char *s, long len);
-void           lua_pushstring 		(const char *s);
-void           lua_pushcclosure		(lua_CFunction fn, int n);
-void           lua_pushusertag          (void *u, int tag);
-void           lua_pushobject       	(lua_Object object);
+void 	       lua_pushnil (lua_State *L);
+void           lua_pushnumber (lua_State *L, double n);
+void           lua_pushlstring (lua_State *L, const char *s, long len);
+void           lua_pushstring (lua_State *L, const char *s);
+void           lua_pushcclosure (lua_State *L, lua_CFunction fn, int n);
+void           lua_pushusertag (lua_State *L, void *u, int tag);
+void           lua_pushobject (lua_State *L, lua_Object object);
 
-lua_Object     lua_pop			(void);
+lua_Object     lua_pop (lua_State *L);
 
-lua_Object     lua_getglobal 		(const char *name);
-lua_Object     lua_rawgetglobal		(const char *name);
-void           lua_setglobal		(const char *name); /* In: value */
-void           lua_rawsetglobal		(const char *name); /* In: value */
+lua_Object     lua_getglobal (lua_State *L, const char *name);
+lua_Object     lua_rawgetglobal (lua_State *L, const char *name);
+void           lua_setglobal (lua_State *L, const char *name); /* In: value */
+void           lua_rawsetglobal (lua_State *L, const char *name);/* In: value */
 
-void           lua_settable	(void); /* In: table, index, value */
-void           lua_rawsettable	(void); /* In: table, index, value */
-lua_Object     lua_gettable 		(void); /* In: table, index */
-lua_Object     lua_rawgettable		(void); /* In: table, index */
+void           lua_settable (lua_State *L); /* In: table, index, value */
+void           lua_rawsettable (lua_State *L); /* In: table, index, value */
+lua_Object     lua_gettable (lua_State *L); /* In: table, index */
+lua_Object     lua_rawgettable (lua_State *L); /* In: table, index */
 
-int            lua_tag			(lua_Object object);
+int            lua_tag (lua_State *L, lua_Object object);
 
-const char    *lua_nextvar		(const char *varname);  /* Out: value */
-int            lua_next			(lua_Object o, int i);
+const char    *lua_nextvar (lua_State *L, const char *varname); /* Out: value */
+int            lua_next (lua_State *L, lua_Object o, int i);
 						/* Out: ref, value */ 
 
-int            lua_ref			(int lock); /* In: value */
-lua_Object     lua_getref		(int ref);
-void	       lua_unref		(int ref);
+int            lua_ref (lua_State *L, int lock); /* In: value */
+lua_Object     lua_getref (lua_State *L, int ref);
+void	       lua_unref (lua_State *L, int ref);
 
-lua_Object     lua_createtable		(void);
+lua_Object     lua_createtable (lua_State *L);
 
-long	       lua_collectgarbage	(long limit);
+long	       lua_collectgarbage (lua_State *L, long limit);
 
 
-/* =============================================================== */
-/* some useful macros/functions */
+lua_Object     lua_seterrormethod (lua_State *L);  /* In: new method */
 
-#define lua_call(name)		lua_callfunction(lua_getglobal(name))
+lua_State     *lua_setstate (lua_State *st);
 
-#define lua_pushref(ref)	lua_pushobject(lua_getref(ref))
 
-#define lua_refobject(o,l)	(lua_pushobject(o), lua_ref(l))
+/* 
+** ===============================================================
+** some useful macros
+** ===============================================================
+*/
 
-#define lua_register(n,f)	(lua_pushcfunction(f), lua_setglobal(n))
+#ifdef LUA_REENTRANT
 
-#define lua_pushuserdata(u)     lua_pushusertag(u, 0)
+#define lua_call(L,name)	lua_callfunction(L, lua_getglobal(L, name))
+#define lua_pushref(L,ref)	lua_pushobject(L, lua_getref(L, ref))
+#define lua_refobject(L,o,l)	(lua_pushobject(L, o), lua_ref(L, l))
+#define lua_register(L,n,f)	(lua_pushcfunction(L, f), lua_setglobal(L, n))
+#define lua_pushuserdata(L,u)	lua_pushusertag(L, u, 0)
+#define lua_pushcfunction(L,f)	lua_pushcclosure(L, f, 0)
+#define lua_clonetag(L,t)	lua_copytagmethods(L, lua_newtag(L), (t))
 
-#define lua_pushcfunction(f)	lua_pushcclosure(f, 0)
+#else
 
+#define lua_call(name)		lua_callfunction(lua_getglobal(name))
+#define lua_pushref(ref)	lua_pushobject(lua_getref(ref))
+#define lua_refobject(o,l)	(lua_pushobject(o), lua_ref(l))
+#define lua_register(n,f)	(lua_pushcfunction(f), lua_setglobal(n))
+#define lua_pushuserdata(u)	lua_pushusertag(u, 0)
+#define lua_pushcfunction(f)	lua_pushcclosure(f, 0)
 #define lua_clonetag(t)		lua_copytagmethods(lua_newtag(), (t))
 
-lua_Object     lua_seterrormethod (void);  /* In: new method */
-
-/* ==========================================================================
-** for compatibility with old versions. Avoid using these macros/functions
-** If your program does need any of these, define LUA_COMPAT2_5
-*/
-
-
-#ifdef LUA_COMPAT2_5
-
-
+#endif
 
-#define lua_storeglobal		lua_setglobal
 
-#define lua_lockobject(o)  lua_refobject(o,1)
-#define	lua_lock() lua_ref(1)
-#define lua_getlocked lua_getref
-#define	lua_pushlocked lua_pushref
-#define	lua_unlock lua_unref
 
-#define lua_pushliteral(o)  lua_pushstring(o)
+#ifndef LUA_REENTRANT
+/* 
+** ===============================================================
+** Macros for single-state use
+** ===============================================================
+*/
 
-#define lua_getindexed(o,n) (lua_pushobject(o), lua_pushnumber(n), lua_gettable())
-#define lua_getfield(o,f)   (lua_pushobject(o), lua_pushstring(f), lua_gettable())
+extern lua_State *lua_state;
 
-#define lua_getsubscript  lua_gettable
-#define lua_storesubscript  lua_settable
+#define lua_open()		((void)(lua_state?0:(lua_state=lua_newstate())))
+
+#define lua_close()		(lua_close)(lua_state)
+#define lua_setstate(st)	(lua_setstate)(lua_state, st)
+#define lua_settagmethod(tag,event)	(lua_settagmethod)(lua_state, tag,event)
+#define lua_gettagmethod(tag,event)	(lua_gettagmethod)(lua_state, tag,event)
+#define lua_newtag()		(lua_newtag)(lua_state)
+#define lua_copytagmethods(tagto,tagfrom)	\
+		(lua_copytagmethods)(lua_state, tagto,tagfrom)
+#define lua_settag(tag)		(lua_settag)(lua_state, tag)
+#define lua_error(s)		(lua_error)(lua_state, s)
+#define lua_dofile(filename)	(lua_dofile)(lua_state, filename)
+#define lua_dostring(string)	(lua_dostring)(lua_state, string)
+#define lua_callfunction(f)	(lua_callfunction)(lua_state, f)
+#define lua_beginblock()	(lua_beginblock)(lua_state)
+#define lua_endblock()		(lua_endblock)(lua_state)
+#define lua_lua2C(number)	(lua_lua2C)(lua_state, number)
+#define lua_type(object)	(lua_type)(lua_state, object)
+#define lua_isnil(object)	(lua_isnil)(lua_state, object)
+#define lua_istable(object)	(lua_istable)(lua_state, object)
+#define lua_isuserdata(object)	(lua_isuserdata)(lua_state, object)
+#define lua_iscfunction(object)	(lua_iscfunction)(lua_state, object)
+#define lua_isnumber(object)	(lua_isnumber)(lua_state, object)
+#define lua_isstring(object)	(lua_isstring)(lua_state, object)
+#define lua_isfunction(object)	(lua_isfunction)(lua_state, object)
+#define lua_equalobj(o1,o2)	(lua_equalobj)(lua_state, o1,o2)
+#define lua_getnumber(object)	(lua_getnumber)(lua_state, object)
+#define lua_getstring(object)	(lua_getstring)(lua_state, object)
+#define lua_strlen(object)	(lua_strlen)(lua_state, object)
+#define lua_getcfunction(object)	(lua_getcfunction)(lua_state, object)
+#define lua_getuserdata(object)	(lua_getuserdata)(lua_state, object)
+#define lua_pushnil()		(lua_pushnil)(lua_state)
+#define lua_pushnumber(n)	(lua_pushnumber)(lua_state, n)
+#define lua_pushlstring(s,len)	(lua_pushlstring)(lua_state, s,len)
+#define lua_pushstring(s)	(lua_pushstring)(lua_state, s)
+#define lua_pushcclosure(fn,n)	(lua_pushcclosure)(lua_state, fn,n)
+#define lua_pushusertag(u,tag)	(lua_pushusertag)(lua_state, u,tag)
+#define lua_pushobject(object)	(lua_pushobject)(lua_state, object)
+#define lua_pop()		(lua_pop)(lua_state)
+#define lua_getglobal(name)	(lua_getglobal)(lua_state, name)
+#define lua_rawgetglobal(name)	(lua_rawgetglobal)(lua_state, name)
+#define lua_setglobal(name)	(lua_setglobal)(lua_state, name)
+#define lua_rawsetglobal(name)	(lua_rawsetglobal)(lua_state, name)
+#define lua_settable()		(lua_settable)(lua_state)
+#define lua_rawsettable()	(lua_rawsettable)(lua_state)
+#define lua_gettable()		(lua_gettable)(lua_state)
+#define lua_rawgettable()	(lua_rawgettable)(lua_state)
+#define lua_tag(object)		(lua_tag)(lua_state, object)
+#define lua_nextvar(varname)	(lua_nextvar)(lua_state, varname)
+#define lua_next(o,i)		(lua_next)(lua_state, o,i)
+#define lua_ref(lock)		(lua_ref)(lua_state, lock)
+#define lua_getref(ref)		(lua_getref)(lua_state, ref)
+#define lua_unref(ref)		(lua_unref)(lua_state, ref)
+#define lua_createtable()	(lua_createtable)(lua_state)
+#define lua_collectgarbage(limit)	(lua_collectgarbage)(lua_state, limit)
+#define lua_seterrormethod()	(lua_seterrormethod)(lua_state)
 
 #endif
 
+
 #endif
 
 

+ 13 - 13
luadebug.h

@@ -1,5 +1,5 @@
 /*
-** $Id: luadebug.h,v 1.6 1999/03/04 21:17:26 roberto Exp roberto $
+** $Id: luadebug.h,v 1.7 1999/08/16 20:52:00 roberto Exp roberto $
 ** Debugging API
 ** See Copyright Notice in lua.h
 */
@@ -13,23 +13,23 @@
 
 typedef lua_Object lua_Function;
 
-typedef void (*lua_LHFunction) (int line);
-typedef void (*lua_CHFunction) (lua_Function func, const char *file, int line);
+typedef void (*lua_LHFunction) (lua_State *L, int line);
+typedef void (*lua_CHFunction) (lua_State *L, lua_Function func, const char *file, int line);
 
-lua_Function lua_stackedfunction (int level);
-void lua_funcinfo (lua_Object func, const char **source, int *linedefined);
-int lua_currentline (lua_Function func);
-const char *lua_getobjname (lua_Object o, const char **name);
+lua_Function lua_stackedfunction (lua_State *L, int level);
+void lua_funcinfo (lua_State *L, lua_Object func, const char **source, int *linedefined);
+int lua_currentline (lua_State *L, lua_Function func);
+const char *lua_getobjname (lua_State *L, lua_Object o, const char **name);
 
-lua_Object lua_getlocal (lua_Function func, int local_number,
+lua_Object lua_getlocal (lua_State *L, lua_Function func, int local_number,
                          const char **name);
-int lua_setlocal (lua_Function func, int local_number);
+int lua_setlocal (lua_State *L, lua_Function func, int local_number);
 
-int lua_nups (lua_Function func);
+int lua_nups (lua_State *L, lua_Function func);
 
-lua_LHFunction lua_setlinehook (lua_LHFunction func);
-lua_CHFunction lua_setcallhook (lua_CHFunction func);
-int lua_setdebug (int debug);
+lua_LHFunction lua_setlinehook (lua_State *L, lua_LHFunction func);
+lua_CHFunction lua_setcallhook (lua_State *L, lua_CHFunction func);
+int lua_setdebug (lua_State *L, int debug);
 
 
 #endif

+ 21 - 12
lualib.h

@@ -1,5 +1,5 @@
 /*
-** $Id: lualib.h,v 1.6 1999/05/05 19:23:11 roberto Exp roberto $
+** $Id: lualib.h,v 1.7 1999/08/16 20:52:00 roberto Exp roberto $
 ** Lua standard libraries
 ** See Copyright Notice in lua.h
 */
@@ -10,27 +10,36 @@
 
 #include "lua.h"
 
-void lua_iolibopen   (void);
-void lua_strlibopen  (void);
-void lua_mathlibopen (void);
-void lua_dblibopen   (void);
+void lua_iolibopen (lua_State *L);
+void lua_strlibopen (lua_State *L);
+void lua_mathlibopen (lua_State *L);
+void lua_dblibopen (lua_State *L);
 
 
-void lua_userinit (void);
+void lua_userinit (lua_State *L);
 
 
-/* To keep compatibility with old versions */
+/* 
+** ===============================================================
+** Macros for single-state use
+** ===============================================================
+*/
+
+#ifndef LUA_REENTRANT
 
-#define iolib_open	lua_iolibopen
-#define strlib_open	lua_strlibopen
-#define mathlib_open	lua_mathlibopen
+#define lua_iolibopen()		(lua_iolibopen)(lua_state)
+#define lua_strlibopen()	(lua_strlibopen)(lua_state)
+#define lua_mathlibopen()	(lua_mathlibopen)(lua_state)
+#define lua_dblibopen()		(lua_dblibopen)(lua_state)
+#define lua_userinit()		(lua_userinit)(lua_state)
+
+#endif
 
 
 
 /* Auxiliary functions (private) */
 
-const char *luaI_classend (const char *p);
+const char *luaI_classend (lua_State *L, const char *p);
 int luaI_singlematch (int c, const char *p, const char *ep);
 
 #endif
-

+ 77 - 75
lundump.c

@@ -1,9 +1,11 @@
 /*
-** $Id: lundump.c,v 1.13 1999/08/16 20:52:00 roberto Exp roberto $
+** $Id: lundump.c,v 1.14 1999/09/06 13:55:09 roberto Exp roberto $
 ** load bytecodes from files
 ** See Copyright Notice in lua.h
 */
 
+#define LUA_REENTRANT
+
 #include <stdio.h>
 #include <string.h>
 #include "lauxlib.h"
@@ -13,195 +15,195 @@
 #include "lstring.h"
 #include "lundump.h"
 
-#define	LoadBlock(b,size,Z)	ezread(Z,b,size)
+#define	LoadBlock(L, b,size,Z)	ezread(L, Z,b,size)
 
-static void unexpectedEOZ (ZIO* Z)
+static void unexpectedEOZ (lua_State *L, ZIO* Z)
 {
- luaL_verror("unexpected end of file in %s",zname(Z));
+ luaL_verror(L, "unexpected end of file in %s",zname(Z));
 }
 
-static int ezgetc (ZIO* Z)
+static int ezgetc (lua_State *L, ZIO* Z)
 {
  int c=zgetc(Z);
- if (c==EOZ) unexpectedEOZ(Z);
+ if (c==EOZ) unexpectedEOZ(L, Z);
  return c;
 }
 
-static void ezread (ZIO* Z, void* b, int n)
+static void ezread (lua_State *L, ZIO* Z, void* b, int n)
 {
  int r=zread(Z,b,n);
- if (r!=0) unexpectedEOZ(Z);
+ if (r!=0) unexpectedEOZ(L, Z);
 }
 
-static unsigned int LoadWord (ZIO* Z)
+static unsigned int LoadWord (lua_State *L, ZIO* Z)
 {
- unsigned int hi=ezgetc(Z);
- unsigned int lo=ezgetc(Z);
+ unsigned int hi=ezgetc(L, Z);
+ unsigned int lo=ezgetc(L, Z);
  return (hi<<8)|lo;
 }
 
-static unsigned long LoadLong (ZIO* Z)
+static unsigned long LoadLong (lua_State *L, ZIO* Z)
 {
- unsigned long hi=LoadWord(Z);
- unsigned long lo=LoadWord(Z);
+ unsigned long hi=LoadWord(L, Z);
+ unsigned long lo=LoadWord(L, Z);
  return (hi<<16)|lo;
 }
 
 /*
 * convert number from text
 */
-real luaU_str2d (const char* b, const char* where)
+real luaU_str2d (lua_State *L, const char* b, const char* where)
 {
  real x;
  if (!luaO_str2d(b, &x))
-   luaL_verror("cannot convert number '%s' in %s",b,where);
+   luaL_verror(L, "cannot convert number '%s' in %s",b,where);
  return x;
 }
 
-static real LoadNumber (ZIO* Z, int native)
+static real LoadNumber (lua_State *L, ZIO* Z, int native)
 {
  real x;
  if (native)
  {
-  LoadBlock(&x,sizeof(x),Z);
+  LoadBlock(L, &x,sizeof(x),Z);
   return x;
  }
  else
  {
   char b[256];
-  int size=ezgetc(Z);
-  LoadBlock(b,size,Z);
+  int size=ezgetc(L, Z);
+  LoadBlock(L, b,size,Z);
   b[size]=0;
-  return luaU_str2d(b,zname(Z));
+  return luaU_str2d(L, b,zname(Z));
  }
 }
 
-static int LoadInt (ZIO* Z, const char* message)
+static int LoadInt (lua_State *L, ZIO* Z, const char* message)
 {
- unsigned long l=LoadLong(Z);
+ unsigned long l=LoadLong(L, Z);
  unsigned int i=l;
- if (i!=l) luaL_verror(message,l,zname(Z));
+ if (i!=l) luaL_verror(L, message,l,zname(Z));
  return i;
 }
 
 #define PAD	5			/* two word operands plus opcode */
 
-static Byte* LoadCode (ZIO* Z)
+static Byte* LoadCode (lua_State *L, ZIO* Z)
 {
- int size=LoadInt(Z,"code too long (%ld bytes) in %s");
- Byte* b=luaM_malloc(size+PAD);
- LoadBlock(b,size,Z);
- if (b[size-1]!=ENDCODE) luaL_verror("bad code in %s",zname(Z));
+ int size=LoadInt(L, Z,"code too long (%ld bytes) in %s");
+ Byte* b=luaM_malloc(L, size+PAD);
+ LoadBlock(L, b,size,Z);
+ if (b[size-1]!=ENDCODE) luaL_verror(L, "bad code in %s",zname(Z));
  memset(b+size,ENDCODE,PAD);		/* pad code for safety */
  return b;
 }
 
-static TaggedString* LoadTString (ZIO* Z)
+static TaggedString* LoadTString (lua_State *L, ZIO* Z)
 {
- long size=LoadLong(Z);
+ long size=LoadLong(L, Z);
  if (size==0)
   return NULL;
  else
  {
-  char* s=luaL_openspace(size);
-  LoadBlock(s,size,Z);
-  return luaS_newlstr(s,size-1);
+  char* s=luaL_openspace(L, size);
+  LoadBlock(L, s,size,Z);
+  return luaS_newlstr(L, s,size-1);
  }
 }
 
-static void LoadLocals (TProtoFunc* tf, ZIO* Z)
+static void LoadLocals (lua_State *L, TProtoFunc* tf, ZIO* Z)
 {
- int i,n=LoadInt(Z,"too many locals (%ld) in %s");
+ int i,n=LoadInt(L, Z,"too many locals (%ld) in %s");
  if (n==0) return;
- tf->locvars=luaM_newvector(n+1,LocVar);
+ tf->locvars=luaM_newvector(L, n+1,LocVar);
  for (i=0; i<n; i++)
  {
-  tf->locvars[i].line=LoadInt(Z,"too many lines (%ld) in %s");
-  tf->locvars[i].varname=LoadTString(Z);
+  tf->locvars[i].line=LoadInt(L, Z,"too many lines (%ld) in %s");
+  tf->locvars[i].varname=LoadTString(L, Z);
  }
  tf->locvars[i].line=-1;		/* flag end of vector */
  tf->locvars[i].varname=NULL;
 }
 
-static TProtoFunc* LoadFunction (ZIO* Z, int native);
+static TProtoFunc* LoadFunction (lua_State *L, ZIO* Z, int native);
 
-static void LoadConstants (TProtoFunc* tf, ZIO* Z, int native)
+static void LoadConstants (lua_State *L, TProtoFunc* tf, ZIO* Z, int native)
 {
- int i,n=LoadInt(Z,"too many constants (%ld) in %s");
+ int i,n=LoadInt(L, Z,"too many constants (%ld) in %s");
  tf->nconsts=n;
  if (n==0) return;
- tf->consts=luaM_newvector(n,TObject);
+ tf->consts=luaM_newvector(L, n,TObject);
  for (i=0; i<n; i++)
  {
   TObject* o=tf->consts+i;
-  ttype(o)=-ezgetc(Z);			/* ttype(o) is negative - ORDER LUA_T */
+  ttype(o)=-ezgetc(L, Z);			/* ttype(o) is negative - ORDER LUA_T */
   switch (ttype(o))
   {
    case LUA_T_NUMBER:
-	nvalue(o)=LoadNumber(Z,native);
+	nvalue(o)=LoadNumber(L, Z,native);
 	break;
    case LUA_T_STRING:
-	tsvalue(o)=LoadTString(Z);
+	tsvalue(o)=LoadTString(L, Z);
 	break;
    case LUA_T_PROTO:
-	tfvalue(o)=LoadFunction(Z,native);
+	tfvalue(o)=LoadFunction(L, Z,native);
 	break;
    case LUA_T_NIL:
 	break;
    default:				/* cannot happen */
-	luaU_badconstant("load",i,o,tf);
+	luaU_badconstant(L, "load",i,o,tf);
 	break;
   }
  }
 }
 
-static TProtoFunc* LoadFunction (ZIO* Z, int native)
+static TProtoFunc* LoadFunction (lua_State *L, ZIO* Z, int native)
 {
- TProtoFunc* tf=luaF_newproto();
- tf->lineDefined=LoadInt(Z,"lineDefined too large (%ld) in %s");
- tf->source=LoadTString(Z);
- if (tf->source==NULL) tf->source=luaS_new(zname(Z));
- tf->code=LoadCode(Z);
- LoadLocals(tf,Z);
- LoadConstants(tf,Z,native);
+ TProtoFunc* tf=luaF_newproto(L);
+ tf->lineDefined=LoadInt(L, Z,"lineDefined too large (%ld) in %s");
+ tf->source=LoadTString(L, Z);
+ if (tf->source==NULL) tf->source=luaS_new(L, zname(Z));
+ tf->code=LoadCode(L, Z);
+ LoadLocals(L, tf,Z);
+ LoadConstants(L, tf,Z,native);
  return tf;
 }
 
-static void LoadSignature (ZIO* Z)
+static void LoadSignature (lua_State *L, ZIO* Z)
 {
  const char* s=SIGNATURE;
- while (*s!=0 && ezgetc(Z)==*s)
+ while (*s!=0 && ezgetc(L, Z)==*s)
   ++s;
- if (*s!=0) luaL_verror("bad signature in %s",zname(Z));
+ if (*s!=0) luaL_verror(L, "bad signature in %s",zname(Z));
 }
 
-static int LoadHeader (ZIO* Z)
+static int LoadHeader (lua_State *L, ZIO* Z)
 {
  int version,sizeofR;
  int native;
- LoadSignature(Z);
- version=ezgetc(Z);
+ LoadSignature(L, Z);
+ version=ezgetc(L, Z);
  if (version>VERSION)
-  luaL_verror(
+  luaL_verror(L, 
 	"%s too new: version=0x%02x; expected at most 0x%02x",
 	zname(Z),version,VERSION);
  if (version<VERSION0)			/* check last major change */
-  luaL_verror(
+  luaL_verror(L, 
 	"%s too old: version=0x%02x; expected at least 0x%02x",
 	zname(Z),version,VERSION0);
- sizeofR=ezgetc(Z);
+ sizeofR=ezgetc(L, Z);
  native=(sizeofR!=0);
  if (native)				/* test number representation */
  {
   if (sizeofR!=sizeof(real))
-   luaL_verror("unknown number size in %s: read %d; expected %d",
+   luaL_verror(L, "unknown number size in %s: read %d; expected %d",
 	 zname(Z),sizeofR,sizeof(real));
   else
   {
    real tf=TEST_NUMBER;
-   real f=LoadNumber(Z,native);
+   real f=LoadNumber(L, Z,native);
    if ((long)f!=(long)tf)
-    luaL_verror("unknown number format in %s: "
+    luaL_verror(L, "unknown number format in %s: "
 	  "read " NUMBER_FMT "; expected " NUMBER_FMT,
 	  zname(Z),f,tf);
   }
@@ -209,31 +211,31 @@ static int LoadHeader (ZIO* Z)
  return native;
 }
 
-static TProtoFunc* LoadChunk (ZIO* Z)
+static TProtoFunc* LoadChunk (lua_State *L, ZIO* Z)
 {
- return LoadFunction(Z,LoadHeader(Z));
+ return LoadFunction(L, Z,LoadHeader(L, Z));
 }
 
 /*
 ** load one chunk from a file or buffer
 ** return main if ok and NULL at EOF
 */
-TProtoFunc* luaU_undump1 (ZIO* Z)
+TProtoFunc* luaU_undump1 (lua_State *L, ZIO* Z)
 {
  int c=zgetc(Z);
  if (c==ID_CHUNK)
-  return LoadChunk(Z);
+  return LoadChunk(L, Z);
  else if (c!=EOZ)
-  luaL_verror("%s is not a Lua binary file",zname(Z));
+  luaL_verror(L, "%s is not a Lua binary file",zname(Z));
  return NULL;
 }
 
 /*
 * handle constants that cannot happen
 */
-void luaU_badconstant (const char* s, int i, const TObject* o, TProtoFunc* tf)
+void luaU_badconstant (lua_State *L, const char* s, int i, const TObject* o, TProtoFunc* tf)
 {
  int t=ttype(o);
  const char* name= (t>0 || t<LUA_T_LINE) ? "?" : luaO_typenames[-t];
- luaL_verror("cannot %s constant #%d: type=%d [%s]" IN,s,i,t,name,INLOC);
+ luaL_verror(L, "cannot %s constant #%d: type=%d [%s]" IN,s,i,t,name,INLOC);
 }

+ 4 - 4
lundump.h

@@ -1,5 +1,5 @@
 /*
-** $Id: lundump.h,v 1.9 1999/07/08 12:43:23 roberto Exp roberto $
+** $Id: lundump.h,v 1.10 1999/08/16 20:52:00 roberto Exp roberto $
 ** load pre-compiled Lua chunks
 ** See Copyright Notice in lua.h
 */
@@ -10,10 +10,10 @@
 #include "lobject.h"
 #include "lzio.h"
 
-TProtoFunc* luaU_undump1 (ZIO* Z);	/* load one chunk */
-void luaU_badconstant (const char* s, int i, const TObject* o, TProtoFunc* tf);
+TProtoFunc* luaU_undump1 (lua_State *L, ZIO* Z);	/* load one chunk */
+void luaU_badconstant (lua_State *L, const char* s, int i, const TObject* o, TProtoFunc* tf);
 					/* handle cases that cannot happen */
-double luaU_str2d (const char* b, const char* where);
+double luaU_str2d (lua_State *L, const char* b, const char* where);
 					/* convert number from text */
 
 /* definitions for headers of binary files */

+ 113 - 111
lvm.c

@@ -1,5 +1,5 @@
 /*
-** $Id: lvm.c,v 1.64 1999/10/14 19:46:57 roberto Exp roberto $
+** $Id: lvm.c,v 1.65 1999/11/04 17:22:26 roberto Exp roberto $
 ** Lua virtual machine
 ** See Copyright Notice in lua.h
 */
@@ -9,6 +9,8 @@
 #include <stdlib.h>
 #include <string.h>
 
+#define LUA_REENTRANT
+
 #include "lauxlib.h"
 #include "ldo.h"
 #include "lfunc.h"
@@ -27,7 +29,7 @@
 #endif
 
 
-#define highbyte(x)	((x)<<8)
+#define highbyte(L, x)	((x)<<8)
 
 
 /* Extra stack size to run a function: LUA_T_LINE(1), TM calls(2), ... */
@@ -35,13 +37,13 @@
 
 
 
-static TaggedString *strconc (const TaggedString *l, const TaggedString *r) {
+static TaggedString *strconc (lua_State *L, const TaggedString *l, const TaggedString *r) {
   long nl = l->u.s.len;
   long nr = r->u.s.len;
-  char *buffer = luaL_openspace(nl+nr);
+  char *buffer = luaL_openspace(L, nl+nr);
   memcpy(buffer, l->str, nl);
   memcpy(buffer+nl, r->str, nr);
-  return luaS_newlstr(buffer, nl+nr);
+  return luaS_newlstr(L, buffer, nl+nr);
 }
 
 
@@ -57,31 +59,31 @@ int luaV_tonumber (TObject *obj) {  /* LUA_NUMBER */
 }
 
 
-int luaV_tostring (TObject *obj) {  /* LUA_NUMBER */
+int luaV_tostring (lua_State *L, TObject *obj) {  /* LUA_NUMBER */
   if (ttype(obj) != LUA_T_NUMBER)
     return 1;
   else {
     char s[32];  /* 16 digits, signal, point and \0  (+ some extra...) */
     sprintf(s, "%.16g", (double)nvalue(obj));
-    tsvalue(obj) = luaS_new(s);
+    tsvalue(obj) = luaS_new(L, s);
     ttype(obj) = LUA_T_STRING;
     return 0;
   }
 }
 
 
-void luaV_setn (Hash *t, int val) {
+void luaV_setn (lua_State *L, Hash *t, int val) {
   TObject index, value;
-  ttype(&index) = LUA_T_STRING; tsvalue(&index) = luaS_new("n");
+  ttype(&index) = LUA_T_STRING; tsvalue(&index) = luaS_new(L, "n");
   ttype(&value) = LUA_T_NUMBER; nvalue(&value) = val;
-  luaH_set(t, &index, &value);
+  luaH_set(L, t, &index, &value);
 }
 
 
-void luaV_closure (int nelems) {
+void luaV_closure (lua_State *L, int nelems) {
   if (nelems > 0) {
     struct Stack *S = &L->stack;
-    Closure *c = luaF_newclosure(nelems);
+    Closure *c = luaF_newclosure(L, nelems);
     c->consts[0] = *(S->top-1);
     memcpy(&c->consts[1], S->top-(nelems+1), nelems*sizeof(TObject));
     S->top -= nelems;
@@ -95,23 +97,23 @@ void luaV_closure (int nelems) {
 ** Function to index a table.
 ** Receives the table at top-2 and the index at top-1.
 */
-void luaV_gettable (void) {
+void luaV_gettable (lua_State *L) {
   TObject *table = L->stack.top-2;
   const TObject *im;
   if (ttype(table) != LUA_T_ARRAY) {  /* not a table, get gettable method */
-    im = luaT_getimbyObj(table, IM_GETTABLE);
+    im = luaT_getimbyObj(L, table, IM_GETTABLE);
     if (ttype(im) == LUA_T_NIL)
-      lua_error("indexed expression not a table");
+      lua_error(L, "indexed expression not a table");
   }
   else {  /* object is a table... */
     int tg = table->value.a->htag;
-    im = luaT_getim(tg, IM_GETTABLE);
+    im = luaT_getim(L, tg, IM_GETTABLE);
     if (ttype(im) == LUA_T_NIL) {  /* and does not have a "gettable" method */
-      const TObject *h = luaH_get(avalue(table), table+1);
+      const TObject *h = luaH_get(L, avalue(table), table+1);
       if (ttype(h) == LUA_T_NIL &&
-          (ttype(im=luaT_getim(tg, IM_INDEX)) != LUA_T_NIL)) {
+          (ttype(im=luaT_getim(L, tg, IM_INDEX)) != LUA_T_NIL)) {
         /* result is nil and there is an "index" tag method */
-        luaD_callTM(im, 2, 1);  /* calls it */
+        luaD_callTM(L, im, 2, 1);  /* calls it */
       }
       else {
         L->stack.top--;
@@ -122,25 +124,25 @@ void luaV_gettable (void) {
     /* else it has a "gettable" method, go through to next command */
   }
   /* object is not a table, or it has a "gettable" method */
-  luaD_callTM(im, 2, 1);
+  luaD_callTM(L, im, 2, 1);
 }
 
 
 /*
 ** Receives table at *t, index at *(t+1) and value at top.
 */
-void luaV_settable (const TObject *t) {
+void luaV_settable (lua_State *L, const TObject *t) {
   struct Stack *S = &L->stack;
   const TObject *im;
   if (ttype(t) != LUA_T_ARRAY) {  /* not a table, get "settable" method */
-    im = luaT_getimbyObj(t, IM_SETTABLE);
+    im = luaT_getimbyObj(L, t, IM_SETTABLE);
     if (ttype(im) == LUA_T_NIL)
-      lua_error("indexed expression not a table");
+      lua_error(L, "indexed expression not a table");
   }
   else {  /* object is a table... */
-    im = luaT_getim(avalue(t)->htag, IM_SETTABLE);
+    im = luaT_getim(L, avalue(t)->htag, IM_SETTABLE);
     if (ttype(im) == LUA_T_NIL) {  /* and does not have a "settable" method */
-      luaH_set(avalue(t), t+1, S->top-1);
+      luaH_set(L, avalue(t), t+1, S->top-1);
       S->top--;  /* pop value */
       return;
     }
@@ -152,35 +154,35 @@ void luaV_settable (const TObject *t) {
   *(S->top) = *(t+1);
   *(S->top-1) = *t;
   S->top += 2;  /* WARNING: caller must assure stack space */
-  luaD_callTM(im, 3, 0);
+  luaD_callTM(L, im, 3, 0);
 }
 
 
-void luaV_rawsettable (const TObject *t) {
+void luaV_rawsettable (lua_State *L, const TObject *t) {
   if (ttype(t) != LUA_T_ARRAY)
-    lua_error("indexed expression not a table");
+    lua_error(L, "indexed expression not a table");
   else {
     struct Stack *S = &L->stack;
-    luaH_set(avalue(t), t+1, S->top-1);
+    luaH_set(L, avalue(t), t+1, S->top-1);
     S->top -= 3;
   }
 }
 
 
-void luaV_getglobal (GlobalVar *gv) {
+void luaV_getglobal (lua_State *L, GlobalVar *gv) {
   /* WARNING: caller must assure stack space */
   const TObject *value = &gv->value;
   switch (ttype(value)) {
     /* only userdata, tables and nil can have getglobal tag methods */
     case LUA_T_USERDATA: case LUA_T_ARRAY: case LUA_T_NIL: {
-      TObject *im = luaT_getimbyObj(value, IM_GETGLOBAL);
+      TObject *im = luaT_getimbyObj(L, value, IM_GETGLOBAL);
       if (ttype(im) != LUA_T_NIL) {  /* is there a tag method? */
         struct Stack *S = &L->stack;
         ttype(S->top) = LUA_T_STRING;
         tsvalue(S->top) = gv->name;  /* global name */
         S->top++;
         *S->top++ = *value;
-        luaD_callTM(im, 2, 1);
+        luaD_callTM(L, im, 2, 1);
         return;
       }
       /* else no tag method: go through to default behavior */
@@ -190,9 +192,9 @@ void luaV_getglobal (GlobalVar *gv) {
 }
 
 
-void luaV_setglobal (GlobalVar *gv) {
+void luaV_setglobal (lua_State *L, GlobalVar *gv) {
   const TObject *oldvalue = &gv->value;
-  const TObject *im = luaT_getimbyObj(oldvalue, IM_SETGLOBAL);
+  const TObject *im = luaT_getimbyObj(L, oldvalue, IM_SETGLOBAL);
   if (ttype(im) == LUA_T_NIL)  /* is there a tag method? */
     gv->value = *(--L->stack.top);
   else {
@@ -204,29 +206,29 @@ void luaV_setglobal (GlobalVar *gv) {
     tsvalue(S->top-1) = gv->name;
     *S->top++ = *oldvalue;
     *S->top++ = newvalue;
-    luaD_callTM(im, 3, 0);
+    luaD_callTM(L, im, 3, 0);
   }
 }
 
 
-static void call_binTM (IMS event, const char *msg) {
+static void call_binTM (lua_State *L, IMS event, const char *msg) {
   /* try first operand */
-  const TObject *im = luaT_getimbyObj(L->stack.top-2, event);
+  const TObject *im = luaT_getimbyObj(L, L->stack.top-2, event);
   if (ttype(im) == LUA_T_NIL) {
-    im = luaT_getimbyObj(L->stack.top-1, event);  /* try second operand */
+    im = luaT_getimbyObj(L, L->stack.top-1, event);  /* try second operand */
     if (ttype(im) == LUA_T_NIL) {
-      im = luaT_getim(0, event);  /* try a 'global' i.m. */
+      im = luaT_getim(L, 0, event);  /* try a 'global' i.m. */
       if (ttype(im) == LUA_T_NIL)
-        lua_error(msg);
+        lua_error(L, msg);
     }
   }
-  lua_pushstring(luaT_eventname[event]);
-  luaD_callTM(im, 3, 1);
+  lua_pushstring(L, luaT_eventname[event]);
+  luaD_callTM(L, im, 3, 1);
 }
 
 
-static void call_arith (IMS event) {
-  call_binTM(event, "unexpected type in arithmetic operation");
+static void call_arith (lua_State *L, IMS event) {
+  call_binTM(L, event, "unexpected type in arithmetic operation");
 }
 
 
@@ -246,7 +248,7 @@ static int luaV_strcomp (const char *l, long ll, const char *r, long lr) {
   }
 }
 
-void luaV_comparison (lua_Type ttype_less, lua_Type ttype_equal,
+void luaV_comparison (lua_State *L, lua_Type ttype_less, lua_Type ttype_equal,
                       lua_Type ttype_great, IMS op) {
   struct Stack *S = &L->stack;
   const TObject *l = S->top-2;
@@ -258,7 +260,7 @@ void luaV_comparison (lua_Type ttype_less, lua_Type ttype_equal,
     result = luaV_strcomp(svalue(l), tsvalue(l)->u.s.len,
                           svalue(r), tsvalue(r)->u.s.len);
   else {
-    call_binTM(op, "unexpected type in comparison");
+    call_binTM(L, op, "unexpected type in comparison");
     return;
   }
   S->top--;
@@ -268,24 +270,24 @@ void luaV_comparison (lua_Type ttype_less, lua_Type ttype_equal,
 }
 
 
-void luaV_pack (StkId firstel, int nvararg, TObject *tab) {
+void luaV_pack (lua_State *L, StkId firstel, int nvararg, TObject *tab) {
   TObject *firstelem = L->stack.stack+firstel;
   int i;
   Hash *htab;
   if (nvararg < 0) nvararg = 0;
-  htab = avalue(tab) = luaH_new(nvararg+1);  /* +1 for field 'n' */
+  htab = avalue(tab) = luaH_new(L, nvararg+1);  /* +1 for field 'n' */
   ttype(tab) = LUA_T_ARRAY;
   for (i=0; i<nvararg; i++)
-    luaH_setint(htab, i+1, firstelem+i);
-  luaV_setn(htab, nvararg);  /* store counter in field "n" */
+    luaH_setint(L, htab, i+1, firstelem+i);
+  luaV_setn(L, htab, nvararg);  /* store counter in field "n" */
 }
 
 
-static void adjust_varargs (StkId first_extra_arg) {
+static void adjust_varargs (lua_State *L, StkId first_extra_arg) {
   TObject arg;
-  luaV_pack(first_extra_arg,
+  luaV_pack(L, first_extra_arg,
        (L->stack.top-L->stack.stack)-first_extra_arg, &arg);
-  luaD_adjusttop(first_extra_arg);
+  luaD_adjusttop(L, first_extra_arg);
   *L->stack.top++ = arg;
 }
 
@@ -296,18 +298,18 @@ static void adjust_varargs (StkId first_extra_arg) {
 ** [stack+base,top). Returns n such that the the results are between
 ** [stack+n,top).
 */
-StkId luaV_execute (const Closure *cl, const TProtoFunc *tf, StkId base) {
+StkId luaV_execute (lua_State *L, const Closure *cl, const TProtoFunc *tf, StkId base) {
   struct Stack *S = &L->stack;  /* to optimize */
   register const Byte *pc = tf->code;
   const TObject *consts = tf->consts;
   if (L->callhook)
-    luaD_callHook(base, tf, 0);
-  luaD_checkstack((*pc++)+EXTRA_STACK);
+    luaD_callHook(L, base, tf, 0);
+  luaD_checkstack(L, (*pc++)+EXTRA_STACK);
   if (*pc < ZEROVARARG)
-    luaD_adjusttop(base+*(pc++));
+    luaD_adjusttop(L, base+*(pc++));
   else {  /* varargs */
-    luaC_checkGC();
-    adjust_varargs(base+(*pc++)-ZEROVARARG);
+    luaC_checkGC(L);
+    adjust_varargs(L, base+(*pc++)-ZEROVARARG);
   }
   for (;;) {
     register int aux = 0;
@@ -323,11 +325,11 @@ StkId luaV_execute (const Closure *cl, const TProtoFunc *tf, StkId base) {
         goto ret;
 
       case CALL: aux = *pc++;
-        luaD_calln(*pc++, aux);
+        luaD_calln(L, *pc++, aux);
         break;
 
       case TAILCALL: aux = *pc++;
-        luaD_calln(*pc++, MULT_RET);
+        luaD_calln(L, *pc++, MULT_RET);
         base += aux;
         goto ret;
 
@@ -341,21 +343,21 @@ StkId luaV_execute (const Closure *cl, const TProtoFunc *tf, StkId base) {
         S->top -= aux;
         break;
 
-      case PUSHNUMBERW: aux += highbyte(*pc++);
+      case PUSHNUMBERW: aux += highbyte(L, *pc++);
       case PUSHNUMBER:  aux += *pc++;
         ttype(S->top) = LUA_T_NUMBER;
         nvalue(S->top) = aux;
         S->top++;
         break;
 
-      case PUSHNUMBERNEGW: aux += highbyte(*pc++);
+      case PUSHNUMBERNEGW: aux += highbyte(L, *pc++);
       case PUSHNUMBERNEG:  aux += *pc++;
         ttype(S->top) = LUA_T_NUMBER;
         nvalue(S->top) = -aux;
         S->top++;
         break;
 
-      case PUSHCONSTANTW: aux += highbyte(*pc++);
+      case PUSHCONSTANTW: aux += highbyte(L, *pc++);
       case PUSHCONSTANT:  aux += *pc++;
         *S->top++ = consts[aux];
         break;
@@ -368,35 +370,35 @@ StkId luaV_execute (const Closure *cl, const TProtoFunc *tf, StkId base) {
         *S->top++ = *((S->stack+base) + aux);
         break;
 
-      case GETGLOBALW: aux += highbyte(*pc++);
+      case GETGLOBALW: aux += highbyte(L, *pc++);
       case GETGLOBAL:  aux += *pc++;
-        luaV_getglobal(tsvalue(&consts[aux])->u.s.gv);
+        luaV_getglobal(L, tsvalue(&consts[aux])->u.s.gv);
         break;
 
       case GETTABLE:
-        luaV_gettable();
+        luaV_gettable(L);
         break;
 
-      case GETDOTTEDW: aux += highbyte(*pc++);
+      case GETDOTTEDW: aux += highbyte(L, *pc++);
       case GETDOTTED:  aux += *pc++;
         *S->top++ = consts[aux];
-        luaV_gettable();
+        luaV_gettable(L);
         break;
 
-      case PUSHSELFW: aux += highbyte(*pc++);
+      case PUSHSELFW: aux += highbyte(L, *pc++);
       case PUSHSELF:  aux += *pc++; {
         TObject receiver;
         receiver = *(S->top-1);
         *S->top++ = consts[aux];
-        luaV_gettable();
+        luaV_gettable(L);
         *S->top++ = receiver;
         break;
       }
 
-      case CREATEARRAYW: aux += highbyte(*pc++);
+      case CREATEARRAYW: aux += highbyte(L, *pc++);
       case CREATEARRAY:  aux += *pc++;
-        luaC_checkGC();
-        avalue(S->top) = luaH_new(aux);
+        luaC_checkGC(L);
+        avalue(S->top) = luaH_new(L, aux);
         ttype(S->top) = LUA_T_ARRAY;
         S->top++;
         break;
@@ -405,34 +407,34 @@ StkId luaV_execute (const Closure *cl, const TProtoFunc *tf, StkId base) {
         *((S->stack+base) + aux) = *(--S->top);
         break;
 
-      case SETGLOBALW: aux += highbyte(*pc++);
+      case SETGLOBALW: aux += highbyte(L, *pc++);
       case SETGLOBAL:  aux += *pc++;
-        luaV_setglobal(tsvalue(&consts[aux])->u.s.gv);
+        luaV_setglobal(L, tsvalue(&consts[aux])->u.s.gv);
         break;
 
       case SETTABLEPOP:
-        luaV_settable(S->top-3);
+        luaV_settable(L, S->top-3);
         S->top -= 2;  /* pop table and index */
         break;
 
       case SETTABLE:
-        luaV_settable(S->top-3-(*pc++));
+        luaV_settable(L, S->top-3-(*pc++));
         break;
 
-      case SETLISTW: aux += highbyte(*pc++);
+      case SETLISTW: aux += highbyte(L, *pc++);
       case SETLIST:  aux += *pc++; {
         int n = *(pc++);
         Hash *arr = avalue(S->top-n-1);
         aux *= LFIELDS_PER_FLUSH;
         for (; n; n--)
-          luaH_setint(arr, n+aux, --S->top);
+          luaH_setint(L, arr, n+aux, --S->top);
         break;
       }
 
       case SETMAP:  aux = *pc++; {
         Hash *arr = avalue(S->top-(2*aux)-3);
         do {
-          luaH_set(arr, S->top-2, S->top-1);
+          luaH_set(L, arr, S->top-2, S->top-1);
           S->top-=2;
         } while (aux--);
         break;
@@ -449,26 +451,26 @@ StkId luaV_execute (const Closure *cl, const TProtoFunc *tf, StkId base) {
       }
 
        case LTOP:
-         luaV_comparison(LUA_T_NUMBER, LUA_T_NIL, LUA_T_NIL, IM_LT);
+         luaV_comparison(L, LUA_T_NUMBER, LUA_T_NIL, LUA_T_NIL, IM_LT);
          break;
 
       case LEOP:
-        luaV_comparison(LUA_T_NUMBER, LUA_T_NUMBER, LUA_T_NIL, IM_LE);
+        luaV_comparison(L, LUA_T_NUMBER, LUA_T_NUMBER, LUA_T_NIL, IM_LE);
         break;
 
       case GTOP:
-        luaV_comparison(LUA_T_NIL, LUA_T_NIL, LUA_T_NUMBER, IM_GT);
+        luaV_comparison(L, LUA_T_NIL, LUA_T_NIL, LUA_T_NUMBER, IM_GT);
         break;
 
       case GEOP:
-        luaV_comparison(LUA_T_NIL, LUA_T_NUMBER, LUA_T_NUMBER, IM_GE);
+        luaV_comparison(L, LUA_T_NIL, LUA_T_NUMBER, LUA_T_NUMBER, IM_GE);
         break;
 
       case ADDOP: {
         TObject *l = S->top-2;
         TObject *r = S->top-1;
         if (tonumber(r) || tonumber(l))
-          call_arith(IM_ADD);
+          call_arith(L, IM_ADD);
         else {
           nvalue(l) += nvalue(r);
           --S->top;
@@ -480,7 +482,7 @@ StkId luaV_execute (const Closure *cl, const TProtoFunc *tf, StkId base) {
         TObject *l = S->top-2;
         TObject *r = S->top-1;
         if (tonumber(r) || tonumber(l))
-          call_arith(IM_SUB);
+          call_arith(L, IM_SUB);
         else {
           nvalue(l) -= nvalue(r);
           --S->top;
@@ -492,7 +494,7 @@ StkId luaV_execute (const Closure *cl, const TProtoFunc *tf, StkId base) {
         TObject *l = S->top-2;
         TObject *r = S->top-1;
         if (tonumber(r) || tonumber(l))
-          call_arith(IM_MUL);
+          call_arith(L, IM_MUL);
         else {
           nvalue(l) *= nvalue(r);
           --S->top;
@@ -504,7 +506,7 @@ StkId luaV_execute (const Closure *cl, const TProtoFunc *tf, StkId base) {
         TObject *l = S->top-2;
         TObject *r = S->top-1;
         if (tonumber(r) || tonumber(l))
-          call_arith(IM_DIV);
+          call_arith(L, IM_DIV);
         else {
           nvalue(l) /= nvalue(r);
           --S->top;
@@ -513,19 +515,19 @@ StkId luaV_execute (const Closure *cl, const TProtoFunc *tf, StkId base) {
       }
 
       case POWOP:
-        call_binTM(IM_POW, "undefined operation");
+        call_binTM(L, IM_POW, "undefined operation");
         break;
 
       case CONCOP: {
         TObject *l = S->top-2;
         TObject *r = S->top-1;
-        if (tostring(l) || tostring(r))
-          call_binTM(IM_CONCAT, "unexpected type for concatenation");
+        if (tostring(L, l) || tostring(L, r))
+          call_binTM(L, IM_CONCAT, "unexpected type for concatenation");
         else {
-          tsvalue(l) = strconc(tsvalue(l), tsvalue(r));
+          tsvalue(l) = strconc(L, tsvalue(l), tsvalue(r));
           --S->top;
         }
-        luaC_checkGC();
+        luaC_checkGC(L);
         break;
       }
 
@@ -533,7 +535,7 @@ StkId luaV_execute (const Closure *cl, const TProtoFunc *tf, StkId base) {
         if (tonumber(S->top-1)) {
           ttype(S->top) = LUA_T_NIL;
           S->top++;
-          call_arith(IM_UNM);
+          call_arith(L, IM_UNM);
         }
         else
           nvalue(S->top-1) = - nvalue(S->top-1);
@@ -545,72 +547,72 @@ StkId luaV_execute (const Closure *cl, const TProtoFunc *tf, StkId base) {
         nvalue(S->top-1) = 1;
         break;
 
-      case ONTJMPW: aux += highbyte(*pc++);
+      case ONTJMPW: aux += highbyte(L, *pc++);
       case ONTJMP:  aux += *pc++;
         if (ttype(S->top-1) != LUA_T_NIL) pc += aux;
         else S->top--;
         break;
 
-      case ONFJMPW: aux += highbyte(*pc++);
+      case ONFJMPW: aux += highbyte(L, *pc++);
       case ONFJMP:  aux += *pc++;
         if (ttype(S->top-1) == LUA_T_NIL) pc += aux;
         else S->top--;
         break;
 
-      case JMPW: aux += highbyte(*pc++);
+      case JMPW: aux += highbyte(L, *pc++);
       case JMP:  aux += *pc++;
         pc += aux;
         break;
 
-      case IFFJMPW: aux += highbyte(*pc++);
+      case IFFJMPW: aux += highbyte(L, *pc++);
       case IFFJMP:  aux += *pc++;
         if (ttype(--S->top) == LUA_T_NIL) pc += aux;
         break;
 
-      case IFTUPJMPW: aux += highbyte(*pc++);
+      case IFTUPJMPW: aux += highbyte(L, *pc++);
       case IFTUPJMP:  aux += *pc++;
         if (ttype(--S->top) != LUA_T_NIL) pc -= aux;
         break;
 
-      case IFFUPJMPW: aux += highbyte(*pc++);
+      case IFFUPJMPW: aux += highbyte(L, *pc++);
       case IFFUPJMP:  aux += *pc++;
         if (ttype(--S->top) == LUA_T_NIL) pc -= aux;
         break;
 
-      case CLOSUREW: aux += highbyte(*pc++);
+      case CLOSUREW: aux += highbyte(L, *pc++);
       case CLOSURE:  aux += *pc++;
         *S->top++ = consts[aux];
-        luaV_closure(*pc++);
-        luaC_checkGC();
+        luaV_closure(L, *pc++);
+        luaC_checkGC(L);
         break;
 
-      case SETLINEW: aux += highbyte(*pc++);
+      case SETLINEW: aux += highbyte(L, *pc++);
       case SETLINE:  aux += *pc++;
         if ((S->stack+base-1)->ttype != LUA_T_LINE) {
           /* open space for LINE value */
-          luaD_openstack((S->top-S->stack)-base);
+          luaD_openstack(L, (S->top-S->stack)-base);
           base++;
           (S->stack+base-1)->ttype = LUA_T_LINE;
         }
         (S->stack+base-1)->value.i = aux;
         if (L->linehook)
-          luaD_lineHook(aux);
+          luaD_lineHook(L, aux);
         break;
 
-      case LONGARGW: aux += highbyte(*pc++);
+      case LONGARGW: aux += highbyte(L, *pc++);
       case LONGARG:  aux += *pc++;
-        aux = highbyte(highbyte(aux));
+        aux = highbyte(L, highbyte(L, aux));
         goto switchentry;  /* do not reset "aux" */
 
       case CHECKSTACK: aux = *pc++;
-        LUA_ASSERT((S->top-S->stack)-base == aux && S->last >= S->top,
+        LUA_ASSERT(L, (S->top-S->stack)-base == aux && S->last >= S->top,
                    "wrong stack size");
         break;
 
     }
   } ret:
   if (L->callhook)
-    luaD_callHook(0, NULL, 1);
+    luaD_callHook(L, 0, NULL, 1);
   return base;
 }
 

+ 13 - 13
lvm.h

@@ -1,5 +1,5 @@
 /*
-** $Id: lvm.h,v 1.10 1999/10/14 19:46:57 roberto Exp roberto $
+** $Id: lvm.h,v 1.11 1999/11/04 17:22:26 roberto Exp roberto $
 ** Lua virtual machine
 ** See Copyright Notice in lua.h
 */
@@ -14,21 +14,21 @@
 
 
 #define tonumber(o) ((ttype(o) != LUA_T_NUMBER) && (luaV_tonumber(o) != 0))
-#define tostring(o) ((ttype(o) != LUA_T_STRING) && (luaV_tostring(o) != 0))
+#define tostring(L, o) ((ttype(o) != LUA_T_STRING) && (luaV_tostring(L, o) != 0))
 
 
-void luaV_pack (StkId firstel, int nvararg, TObject *tab);
+void luaV_pack (lua_State *L, StkId firstel, int nvararg, TObject *tab);
 int luaV_tonumber (TObject *obj);
-int luaV_tostring (TObject *obj);
-void luaV_setn (Hash *t, int val);
-void luaV_gettable (void);
-void luaV_settable (const TObject *t);
-void luaV_rawsettable (const TObject *t);
-void luaV_getglobal (GlobalVar *gv);
-void luaV_setglobal (GlobalVar *gv);
-StkId luaV_execute (const Closure *cl, const TProtoFunc *tf, StkId base);
-void luaV_closure (int nelems);
-void luaV_comparison (lua_Type ttype_less, lua_Type ttype_equal,
+int luaV_tostring (lua_State *L, TObject *obj);
+void luaV_setn (lua_State *L, Hash *t, int val);
+void luaV_gettable (lua_State *L);
+void luaV_settable (lua_State *L, const TObject *t);
+void luaV_rawsettable (lua_State *L, const TObject *t);
+void luaV_getglobal (lua_State *L, GlobalVar *gv);
+void luaV_setglobal (lua_State *L, GlobalVar *gv);
+StkId luaV_execute (lua_State *L, const Closure *cl, const TProtoFunc *tf, StkId base);
+void luaV_closure (lua_State *L, int nelems);
+void luaV_comparison (lua_State *L, lua_Type ttype_less, lua_Type ttype_equal,
                       lua_Type ttype_great, IMS op);
 
 #endif