aboutsummaryrefslogtreecommitdiff
path: root/ltm.c
diff options
context:
space:
mode:
Diffstat (limited to 'ltm.c')
-rw-r--r--ltm.c63
1 files changed, 36 insertions, 27 deletions
diff --git a/ltm.c b/ltm.c
index 1dfc8a72..1f0ac830 100644
--- a/ltm.c
+++ b/ltm.c
@@ -1,5 +1,5 @@
1/* 1/*
2** $Id: ltm.c,v 1.52 2000/10/03 14:27:44 roberto Exp roberto $ 2** $Id: ltm.c,v 1.53 2000/10/05 12:14:08 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*/
@@ -17,7 +17,7 @@
17#include "ltm.h" 17#include "ltm.h"
18 18
19 19
20const char *const luaT_eventname[] = { /* ORDER IM */ 20const char *const luaT_eventname[] = { /* ORDER TM */
21 "gettable", "settable", "index", "getglobal", "setglobal", "add", "sub", 21 "gettable", "settable", "index", "getglobal", "setglobal", "add", "sub",
22 "mul", "div", "pow", "unm", "lt", "concat", "gc", "function", 22 "mul", "div", "pow", "unm", "lt", "concat", "gc", "function",
23 "le", "gt", "ge", /* deprecated options!! */ 23 "le", "gt", "ge", /* deprecated options!! */
@@ -36,9 +36,9 @@ static int findevent (const char *name) {
36 36
37static int luaI_checkevent (lua_State *L, const char *name, int t) { 37static int luaI_checkevent (lua_State *L, const char *name, int t) {
38 int e = findevent(name); 38 int e = findevent(name);
39 if (e >= IM_N) 39 if (e >= TM_N)
40 luaO_verror(L, "event `%.50s' is deprecated", name); 40 luaO_verror(L, "event `%.50s' is deprecated", name);
41 if (e == IM_GC && t == LUA_TTABLE) 41 if (e == TM_GC && t == LUA_TTABLE)
42 luaO_verror(L, "event `gc' for tables is deprecated"); 42 luaO_verror(L, "event `gc' for tables is deprecated");
43 if (e < 0) 43 if (e < 0)
44 luaO_verror(L, "`%.50s' is not a valid event name", name); 44 luaO_verror(L, "`%.50s' is not a valid event name", name);
@@ -50,8 +50,8 @@ static int luaI_checkevent (lua_State *L, const char *name, int t) {
50/* events in LUA_TNIL are all allowed, since this is used as a 50/* events in LUA_TNIL are all allowed, since this is used as a
51* 'placeholder' for "default" fallbacks 51* 'placeholder' for "default" fallbacks
52*/ 52*/
53/* ORDER LUA_T, ORDER IM */ 53/* ORDER LUA_T, ORDER TM */
54static const char luaT_validevents[NUM_TAGS][IM_N] = { 54static const char luaT_validevents[NUM_TAGS][TM_N] = {
55 {1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1}, /* LUA_TUSERDATA */ 55 {1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1}, /* LUA_TUSERDATA */
56 {1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1}, /* LUA_TNIL */ 56 {1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1}, /* LUA_TNIL */
57 {1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1}, /* LUA_TNUMBER */ 57 {1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1}, /* LUA_TNUMBER */
@@ -67,16 +67,16 @@ int luaT_validevent (int t, int e) { /* ORDER LUA_T */
67 67
68static void init_entry (lua_State *L, int tag) { 68static void init_entry (lua_State *L, int tag) {
69 int i; 69 int i;
70 for (i=0; i<IM_N; i++) 70 for (i=0; i<TM_N; i++)
71 ttype(luaT_getim(L, tag, i)) = LUA_TNIL; 71 luaT_gettm(L, tag, i) = NULL;
72 L->IMtable[tag].collected = NULL; 72 L->TMtable[tag].collected = NULL;
73} 73}
74 74
75 75
76void luaT_init (lua_State *L) { 76void luaT_init (lua_State *L) {
77 int t; 77 int t;
78 luaM_growvector(L, L->IMtable, 0, NUM_TAGS, struct IM, "", MAX_INT); 78 luaM_growvector(L, L->TMtable, 0, NUM_TAGS, struct TM, "", MAX_INT);
79 L->nblocks += NUM_TAGS*sizeof(struct IM); 79 L->nblocks += NUM_TAGS*sizeof(struct TM);
80 L->last_tag = NUM_TAGS-1; 80 L->last_tag = NUM_TAGS-1;
81 for (t=0; t<=L->last_tag; t++) 81 for (t=0; t<=L->last_tag; t++)
82 init_entry(L, t); 82 init_entry(L, t);
@@ -84,9 +84,9 @@ void luaT_init (lua_State *L) {
84 84
85 85
86int lua_newtag (lua_State *L) { 86int lua_newtag (lua_State *L) {
87 luaM_growvector(L, L->IMtable, L->last_tag, 1, struct IM, 87 luaM_growvector(L, L->TMtable, L->last_tag, 1, struct TM,
88 "tag table overflow", MAX_INT); 88 "tag table overflow", MAX_INT);
89 L->nblocks += sizeof(struct IM); 89 L->nblocks += sizeof(struct TM);
90 L->last_tag++; 90 L->last_tag++;
91 init_entry(L, L->last_tag); 91 init_entry(L, L->last_tag);
92 return L->last_tag; 92 return L->last_tag;
@@ -108,9 +108,9 @@ int lua_copytagmethods (lua_State *L, int tagto, int tagfrom) {
108 int e; 108 int e;
109 checktag(L, tagto); 109 checktag(L, tagto);
110 checktag(L, tagfrom); 110 checktag(L, tagfrom);
111 for (e=0; e<IM_N; e++) { 111 for (e=0; e<TM_N; e++) {
112 if (luaT_validevent(tagto, e)) 112 if (luaT_validevent(tagto, e))
113 *luaT_getim(L, tagto, e) = *luaT_getim(L, tagfrom, e); 113 luaT_gettm(L, tagto, e) = luaT_gettm(L, tagfrom, e);
114 } 114 }
115 return tagto; 115 return tagto;
116} 116}
@@ -130,8 +130,10 @@ void lua_gettagmethod (lua_State *L, int t, const char *event) {
130 int e; 130 int e;
131 e = luaI_checkevent(L, event, t); 131 e = luaI_checkevent(L, event, t);
132 checktag(L, t); 132 checktag(L, t);
133 if (luaT_validevent(t, e)) 133 if (luaT_validevent(t, e) && luaT_gettm(L, t, e)) {
134 *L->top = *luaT_getim(L, t,e); 134 clvalue(L->top) = luaT_gettm(L, t, e);
135 ttype(L->top) = LUA_TFUNCTION;
136 }
135 else 137 else
136 ttype(L->top) = LUA_TNIL; 138 ttype(L->top) = LUA_TNIL;
137 incr_top; 139 incr_top;
@@ -139,19 +141,26 @@ void lua_gettagmethod (lua_State *L, int t, const char *event) {
139 141
140 142
141void lua_settagmethod (lua_State *L, int t, const char *event) { 143void lua_settagmethod (lua_State *L, int t, const char *event) {
142 TObject temp; 144 Closure *oldtm;
143 int e; 145 int e = luaI_checkevent(L, event, t);
144 LUA_ASSERT(lua_isnil(L, -1) || lua_isfunction(L, -1),
145 "function or nil expected");
146 e = luaI_checkevent(L, event, t);
147 checktag(L, t); 146 checktag(L, t);
148 if (!luaT_validevent(t, e)) 147 if (!luaT_validevent(t, e))
149 luaO_verror(L, "cannot change `%.20s' tag method for type `%.20s'%.20s", 148 luaO_verror(L, "cannot change `%.20s' tag method for type `%.20s'%.20s",
150 luaT_eventname[e], luaO_typenames[t], 149 luaT_eventname[e], luaO_typenames[t],
151 (t == LUA_TTABLE || t == LUA_TUSERDATA) ? " with default tag" 150 (t == LUA_TTABLE || t == LUA_TUSERDATA) ?
152 : ""); 151 " with default tag" : "");
153 temp = *(L->top - 1); 152 oldtm = luaT_gettm(L, t, e);
154 *(L->top - 1) = *luaT_getim(L, t,e); 153 switch (ttype(L->top - 1)) {
155 *luaT_getim(L, t, e) = temp; 154 case LUA_TNIL:
155 luaT_gettm(L, t, e) = NULL;
156 break;
157 case LUA_TFUNCTION:
158 luaT_gettm(L, t, e) = clvalue(L->top - 1);
159 break;
160 default:
161 lua_error(L, "tag method must be a function (or nil)");
162 }
163 clvalue(L->top - 1) = oldtm;
164 ttype(L->top - 1) = (oldtm ? LUA_TFUNCTION : LUA_TNIL);
156} 165}
157 166