aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRoberto Ierusalimschy <roberto@inf.puc-rio.br>2005-05-05 12:34:03 -0300
committerRoberto Ierusalimschy <roberto@inf.puc-rio.br>2005-05-05 12:34:03 -0300
commit6cf85dcc900c71687678bc316164142e76df7385 (patch)
treec7d672fc9c68f2cdaffb5e57d1bf8c846091aaa0
parent65f4a0f636eede0f026d0205ac929bc5a56f8b9c (diff)
downloadlua-6cf85dcc900c71687678bc316164142e76df7385.tar.gz
lua-6cf85dcc900c71687678bc316164142e76df7385.tar.bz2
lua-6cf85dcc900c71687678bc316164142e76df7385.zip
metatables for all types
-rw-r--r--lapi.c13
-rw-r--r--lgc.c11
-rw-r--r--lstate.c4
-rw-r--r--lstate.h3
-rw-r--r--lstrlib.c17
-rw-r--r--ltm.c8
-rw-r--r--ltm.h3
7 files changed, 45 insertions, 14 deletions
diff --git a/lapi.c b/lapi.c
index 05b801b2..f6244e39 100644
--- a/lapi.c
+++ b/lapi.c
@@ -1,5 +1,5 @@
1/* 1/*
2** $Id: lapi.c,v 2.37 2005/04/04 18:12:51 roberto Exp roberto $ 2** $Id: lapi.c,v 2.38 2005/04/05 15:35:15 roberto Exp roberto $
3** Lua API 3** Lua API
4** See Copyright Notice in lua.h 4** See Copyright Notice in lua.h
5*/ 5*/
@@ -319,7 +319,8 @@ LUA_API lua_Integer lua_tointeger (lua_State *L, int idx) {
319 const TValue *o = index2adr(L, idx); 319 const TValue *o = index2adr(L, idx);
320 if (tonumber(o, &n)) { 320 if (tonumber(o, &n)) {
321 lua_Integer res; 321 lua_Integer res;
322 lua_number2integer(res, nvalue(o)); 322 lua_Number num = nvalue(o);
323 lua_number2integer(res, num);
323 return res; 324 return res;
324 } 325 }
325 else 326 else
@@ -587,6 +588,9 @@ LUA_API int lua_getmetatable (lua_State *L, int objindex) {
587 case LUA_TUSERDATA: 588 case LUA_TUSERDATA:
588 mt = uvalue(obj)->metatable; 589 mt = uvalue(obj)->metatable;
589 break; 590 break;
591 default:
592 mt = G(L)->mt[ttype(obj)];
593 break;
590 } 594 }
591 if (mt == NULL) 595 if (mt == NULL)
592 res = 0; 596 res = 0;
@@ -681,7 +685,6 @@ LUA_API void lua_rawseti (lua_State *L, int idx, int n) {
681LUA_API int lua_setmetatable (lua_State *L, int objindex) { 685LUA_API int lua_setmetatable (lua_State *L, int objindex) {
682 TValue *obj; 686 TValue *obj;
683 Table *mt; 687 Table *mt;
684 int res = 1;
685 lua_lock(L); 688 lua_lock(L);
686 api_checknelems(L, 1); 689 api_checknelems(L, 1);
687 obj = index2adr(L, objindex); 690 obj = index2adr(L, objindex);
@@ -706,13 +709,13 @@ LUA_API int lua_setmetatable (lua_State *L, int objindex) {
706 break; 709 break;
707 } 710 }
708 default: { 711 default: {
709 res = 0; /* cannot set */ 712 G(L)->mt[ttype(obj)] = mt;
710 break; 713 break;
711 } 714 }
712 } 715 }
713 L->top--; 716 L->top--;
714 lua_unlock(L); 717 lua_unlock(L);
715 return res; 718 return 1;
716} 719}
717 720
718 721
diff --git a/lgc.c b/lgc.c
index 8db5fb0d..3d3736f8 100644
--- a/lgc.c
+++ b/lgc.c
@@ -1,5 +1,5 @@
1/* 1/*
2** $Id: lgc.c,v 2.30 2005/03/16 17:00:21 roberto Exp roberto $ 2** $Id: lgc.c,v 2.31 2005/03/22 16:04:29 roberto Exp roberto $
3** Garbage Collector 3** Garbage Collector
4** See Copyright Notice in lua.h 4** See Copyright Notice in lua.h
5*/ 5*/
@@ -493,6 +493,13 @@ void luaC_freeall (lua_State *L) {
493} 493}
494 494
495 495
496static void markmt (global_State *g) {
497 int i;
498 for (i=0; i<NUM_TAGS; i++)
499 if (g->mt[i]) markobject(g, g->mt[i]);
500}
501
502
496/* mark root set */ 503/* mark root set */
497static void markroot (lua_State *L) { 504static void markroot (lua_State *L) {
498 global_State *g = G(L); 505 global_State *g = G(L);
@@ -503,6 +510,7 @@ static void markroot (lua_State *L) {
503 /* make global table be traversed before main stack */ 510 /* make global table be traversed before main stack */
504 markvalue(g, gt(g->mainthread)); 511 markvalue(g, gt(g->mainthread));
505 markvalue(g, registry(L)); 512 markvalue(g, registry(L));
513 markmt(g);
506 g->gcstate = GCSpropagate; 514 g->gcstate = GCSpropagate;
507} 515}
508 516
@@ -529,6 +537,7 @@ static void atomic (lua_State *L) {
529 g->weak = NULL; 537 g->weak = NULL;
530 lua_assert(!iswhite(obj2gco(g->mainthread))); 538 lua_assert(!iswhite(obj2gco(g->mainthread)));
531 markobject(g, L); /* mark running thread */ 539 markobject(g, L); /* mark running thread */
540 markmt(g); /* mark basic metatables (again) */
532 propagateall(g); 541 propagateall(g);
533 /* remark gray again */ 542 /* remark gray again */
534 g->gray = g->grayagain; 543 g->gray = g->grayagain;
diff --git a/lstate.c b/lstate.c
index 872156ea..8bcd14fe 100644
--- a/lstate.c
+++ b/lstate.c
@@ -1,5 +1,5 @@
1/* 1/*
2** $Id: lstate.c,v 2.29 2005/04/05 13:41:29 roberto Exp roberto $ 2** $Id: lstate.c,v 2.30 2005/04/05 15:57:59 roberto Exp roberto $
3** Global State 3** Global State
4** See Copyright Notice in lua.h 4** See Copyright Notice in lua.h
5*/ 5*/
@@ -141,6 +141,7 @@ void luaE_freethread (lua_State *L, lua_State *L1) {
141 141
142 142
143LUA_API lua_State *lua_newstate (lua_Alloc f, void *ud) { 143LUA_API lua_State *lua_newstate (lua_Alloc f, void *ud) {
144 int i;
144 lua_State *L; 145 lua_State *L;
145 global_State *g; 146 global_State *g;
146 void *l = (*f)(ud, NULL, 0, state_size(LG)); 147 void *l = (*f)(ud, NULL, 0, state_size(LG));
@@ -177,6 +178,7 @@ LUA_API lua_State *lua_newstate (lua_Alloc f, void *ud) {
177 g->gcpause = LUAI_GCPAUSE; 178 g->gcpause = LUAI_GCPAUSE;
178 g->gcstepmul = LUAI_GCMUL; 179 g->gcstepmul = LUAI_GCMUL;
179 g->gcdept = 0; 180 g->gcdept = 0;
181 for (i=0; i<NUM_TAGS; i++) g->mt[i] = NULL;
180 if (luaD_rawrunprotected(L, f_luaopen, NULL) != 0) { 182 if (luaD_rawrunprotected(L, f_luaopen, NULL) != 0) {
181 /* memory allocation error: free partial state */ 183 /* memory allocation error: free partial state */
182 close_state(L); 184 close_state(L);
diff --git a/lstate.h b/lstate.h
index 908abf70..6742b4ca 100644
--- a/lstate.h
+++ b/lstate.h
@@ -1,5 +1,5 @@
1/* 1/*
2** $Id: lstate.h,v 2.19 2005/04/05 13:41:29 roberto Exp roberto $ 2** $Id: lstate.h,v 2.20 2005/04/25 19:24:10 roberto Exp roberto $
3** Global State 3** Global State
4** See Copyright Notice in lua.h 4** See Copyright Notice in lua.h
5*/ 5*/
@@ -89,6 +89,7 @@ typedef struct global_State {
89 TValue _registry; 89 TValue _registry;
90 struct lua_State *mainthread; 90 struct lua_State *mainthread;
91 UpVal uvhead; /* head of double-linked list of all open upvalues */ 91 UpVal uvhead; /* head of double-linked list of all open upvalues */
92 struct Table *mt[NUM_TAGS]; /* metatables for basic types */
92 TString *tmname[TM_N]; /* array with tag-method names */ 93 TString *tmname[TM_N]; /* array with tag-method names */
93} global_State; 94} global_State;
94 95
diff --git a/lstrlib.c b/lstrlib.c
index 1a2e6c29..93f8e776 100644
--- a/lstrlib.c
+++ b/lstrlib.c
@@ -1,5 +1,5 @@
1/* 1/*
2** $Id: lstrlib.c,v 1.110 2005/03/08 20:10:05 roberto Exp roberto $ 2** $Id: lstrlib.c,v 1.111 2005/03/22 16:54:29 roberto Exp roberto $
3** Standard library for string operations and pattern-matching 3** Standard library for string operations and pattern-matching
4** See Copyright Notice in lua.h 4** See Copyright Notice in lua.h
5*/ 5*/
@@ -772,11 +772,26 @@ static const luaL_reg strlib[] = {
772}; 772};
773 773
774 774
775static void createmetatable (lua_State *L) {
776 lua_newtable(L); /* create metatable for strings */
777 lua_pushliteral(L, ""); /* dummy string */
778 lua_pushvalue(L, -2);
779 lua_setmetatable(L, -2); /* set string metatable */
780 lua_pop(L, 1); /* pop dummy string */
781 lua_pushvalue(L, -2); /* string library... */
782 lua_setfield(L, -2, "__index"); /* ...is the __index metamethod */
783 lua_getfield(L, -2, "len");
784 lua_setfield(L, -2, "__siz");
785 lua_pop(L, 1); /* pop metatable */
786}
787
788
775/* 789/*
776** Open string library 790** Open string library
777*/ 791*/
778LUALIB_API int luaopen_string (lua_State *L) { 792LUALIB_API int luaopen_string (lua_State *L) {
779 luaL_openlib(L, LUA_STRLIBNAME, strlib, 0); 793 luaL_openlib(L, LUA_STRLIBNAME, strlib, 0);
794 createmetatable(L);
780 return 1; 795 return 1;
781} 796}
782 797
diff --git a/ltm.c b/ltm.c
index ef023528..dc5db074 100644
--- a/ltm.c
+++ b/ltm.c
@@ -1,5 +1,5 @@
1/* 1/*
2** $Id: ltm.c,v 2.3 2004/04/30 20:13:38 roberto Exp roberto $ 2** $Id: ltm.c,v 2.4 2005/03/08 18:00:16 roberto Exp roberto $
3** Tag methods 3** Tag methods
4** See Copyright Notice in lua.h 4** See Copyright Notice in lua.h
5*/ 5*/
@@ -32,7 +32,7 @@ void luaT_init (lua_State *L) {
32 "__index", "__newindex", 32 "__index", "__newindex",
33 "__gc", "__mode", "__eq", 33 "__gc", "__mode", "__eq",
34 "__add", "__sub", "__mul", "__div", "__mod", 34 "__add", "__sub", "__mul", "__div", "__mod",
35 "__pow", "__unm", "__lt", "__le", 35 "__pow", "__unm", "__siz", "__lt", "__le",
36 "__concat", "__call" 36 "__concat", "__call"
37 }; 37 };
38 int i; 38 int i;
@@ -68,8 +68,8 @@ const TValue *luaT_gettmbyobj (lua_State *L, const TValue *o, TMS event) {
68 mt = uvalue(o)->metatable; 68 mt = uvalue(o)->metatable;
69 break; 69 break;
70 default: 70 default:
71 mt = NULL; 71 mt = G(L)->mt[ttype(o)];
72 } 72 }
73 return (mt ? luaH_getstr(mt, G(L)->tmname[event]) : &luaO_nilobject); 73 return (mt ? luaH_getstr(mt, G(L)->tmname[event]) : &luaO_nilobject);
74} 74}
75 75
diff --git a/ltm.h b/ltm.h
index bd007ee8..0039bea7 100644
--- a/ltm.h
+++ b/ltm.h
@@ -1,5 +1,5 @@
1/* 1/*
2** $Id: ltm.h,v 2.2 2005/03/08 18:00:16 roberto Exp roberto $ 2** $Id: ltm.h,v 2.3 2005/04/25 19:24:10 roberto Exp roberto $
3** Tag methods 3** Tag methods
4** See Copyright Notice in lua.h 4** See Copyright Notice in lua.h
5*/ 5*/
@@ -28,6 +28,7 @@ typedef enum {
28 TM_MOD, 28 TM_MOD,
29 TM_POW, 29 TM_POW,
30 TM_UNM, 30 TM_UNM,
31 TM_SIZ,
31 TM_LT, 32 TM_LT,
32 TM_LE, 33 TM_LE,
33 TM_CONCAT, 34 TM_CONCAT,