Subversion Repositories WoWGM

Rev

Details | Last modification | View Log | RSS feed

Rev Author Line No. Line
3 tristanc 1
/*
2
** $Id: lapi.c,v 2.55 2006/06/07 12:37:17 roberto Exp $
3
** Lua API
4
** See Copyright Notice in lua.h
5
*/
6
 
7
 
8
#include <assert.h>
9
#include <math.h>
10
#include <stdarg.h>
11
#include <string.h>
12
 
13
#define lapi_c
14
#define LUA_CORE
15
 
16
#include "lua.h"
17
 
18
#include "lapi.h"
19
#include "ldebug.h"
20
#include "ldo.h"
21
#include "lfunc.h"
22
#include "lgc.h"
23
#include "lmem.h"
24
#include "lobject.h"
25
#include "lstate.h"
26
#include "lstring.h"
27
#include "ltable.h"
28
#include "ltm.h"
29
#include "lundump.h"
30
#include "lvm.h"
31
 
32
 
33
 
34
const char lua_ident[] =
35
  "$Lua: " LUA_RELEASE " " LUA_COPYRIGHT " $\n"
36
  "$Authors: " LUA_AUTHORS " $\n"
37
  "$URL: www.lua.org $\n";
38
 
39
 
40
 
41
#define api_checknelems(L, n)	api_check(L, (n) <= (L->top - L->base))
42
 
43
#define api_checkvalidindex(L, i)	api_check(L, (i) != luaO_nilobject)
44
 
45
#define api_incr_top(L)   {api_check(L, L->top < L->ci->top); L->top++;}
46
 
47
 
48
 
49
static TValue *index2adr (lua_State *L, int idx) {
50
  if (idx > 0) {
51
    TValue *o = L->base + (idx - 1);
52
    api_check(L, idx <= L->ci->top - L->base);
53
    if (o >= L->top) return cast(TValue *, luaO_nilobject);
54
    else return o;
55
  }
56
  else if (idx > LUA_REGISTRYINDEX) {
57
    api_check(L, idx != 0 && -idx <= L->top - L->base);
58
    return L->top + idx;
59
  }
60
  else switch (idx) {  /* pseudo-indices */
61
    case LUA_REGISTRYINDEX: return registry(L);
62
    case LUA_ENVIRONINDEX: {
63
      Closure *func = curr_func(L);
64
      sethvalue(L, &L->env, func->c.env);
65
      return &L->env;
66
    }
67
    case LUA_GLOBALSINDEX: return gt(L);
68
    default: {
69
      Closure *func = curr_func(L);
70
      idx = LUA_GLOBALSINDEX - idx;
71
      return (idx <= func->c.nupvalues)
72
                ? &func->c.upvalue[idx-1]
73
                : cast(TValue *, luaO_nilobject);
74
    }
75
  }
76
}
77
 
78
 
79
static Table *getcurrenv (lua_State *L) {
80
  if (L->ci == L->base_ci)  /* no enclosing function? */
81
    return hvalue(gt(L));  /* use global table as environment */
82
  else {
83
    Closure *func = curr_func(L);
84
    return func->c.env;
85
  }
86
}
87
 
88
 
89
void luaA_pushobject (lua_State *L, const TValue *o) {
90
  setobj2s(L, L->top, o);
91
  api_incr_top(L);
92
}
93
 
94
 
95
LUA_API int lua_checkstack (lua_State *L, int size) {
96
  int res;
97
  lua_lock(L);
98
  if ((L->top - L->base + size) > LUAI_MAXCSTACK)
99
    res = 0;  /* stack overflow */
100
  else {
101
    luaD_checkstack(L, size);
102
    if (L->ci->top < L->top + size)
103
      L->ci->top = L->top + size;
104
    res = 1;
105
  }
106
  lua_unlock(L);
107
  return res;
108
}
109
 
110
 
111
LUA_API void lua_xmove (lua_State *from, lua_State *to, int n) {
112
  int i;
113
  if (from == to) return;
114
  lua_lock(to);
115
  api_checknelems(from, n);
116
  api_check(from, G(from) == G(to));
117
  api_check(from, to->ci->top - to->top >= n);
118
  from->top -= n;
119
  for (i = 0; i < n; i++) {
120
    setobj2s(to, to->top++, from->top + i);
121
  }
122
  lua_unlock(to);
123
}
124
 
125
 
126
LUA_API lua_CFunction lua_atpanic (lua_State *L, lua_CFunction panicf) {
127
  lua_CFunction old;
128
  lua_lock(L);
129
  old = G(L)->panic;
130
  G(L)->panic = panicf;
131
  lua_unlock(L);
132
  return old;
133
}
134
 
135
 
136
LUA_API lua_State *lua_newthread (lua_State *L) {
137
  lua_State *L1;
138
  lua_lock(L);
139
  luaC_checkGC(L);
140
  L1 = luaE_newthread(L);
141
  setthvalue(L, L->top, L1);
142
  api_incr_top(L);
143
  lua_unlock(L);
144
  luai_userstatethread(L, L1);
145
  return L1;
146
}
147
 
148
 
149
 
150
/*
151
** basic stack manipulation
152
*/
153
 
154
 
155
LUA_API int lua_gettop (lua_State *L) {
156
  return cast_int(L->top - L->base);
157
}
158
 
159
 
160
LUA_API void lua_settop (lua_State *L, int idx) {
161
  lua_lock(L);
162
  if (idx >= 0) {
163
    api_check(L, idx <= L->stack_last - L->base);
164
    while (L->top < L->base + idx)
165
      setnilvalue(L->top++);
166
    L->top = L->base + idx;
167
  }
168
  else {
169
    api_check(L, -(idx+1) <= (L->top - L->base));
170
    L->top += idx+1;  /* `subtract' index (index is negative) */
171
  }
172
  lua_unlock(L);
173
}
174
 
175
 
176
LUA_API void lua_remove (lua_State *L, int idx) {
177
  StkId p;
178
  lua_lock(L);
179
  p = index2adr(L, idx);
180
  api_checkvalidindex(L, p);
181
  while (++p < L->top) setobjs2s(L, p-1, p);
182
  L->top--;
183
  lua_unlock(L);
184
}
185
 
186
 
187
LUA_API void lua_insert (lua_State *L, int idx) {
188
  StkId p;
189
  StkId q;
190
  lua_lock(L);
191
  p = index2adr(L, idx);
192
  api_checkvalidindex(L, p);
193
  for (q = L->top; q>p; q--) setobjs2s(L, q, q-1);
194
  setobjs2s(L, p, L->top);
195
  lua_unlock(L);
196
}
197
 
198
 
199
LUA_API void lua_replace (lua_State *L, int idx) {
200
  StkId o;
201
  lua_lock(L);
202
  /* explicit test for incompatible code */
203
  if (idx == LUA_ENVIRONINDEX && L->ci == L->base_ci)
204
    luaG_runerror(L, "no calling environment");
205
  api_checknelems(L, 1);
206
  o = index2adr(L, idx);
207
  api_checkvalidindex(L, o);
208
  if (idx == LUA_ENVIRONINDEX) {
209
    Closure *func = curr_func(L);
210
    api_check(L, ttistable(L->top - 1)); 
211
    func->c.env = hvalue(L->top - 1);
212
    luaC_barrier(L, func, L->top - 1);
213
  }
214
  else {
215
    setobj(L, o, L->top - 1);
216
    if (idx < LUA_GLOBALSINDEX)  /* function upvalue? */
217
      luaC_barrier(L, curr_func(L), L->top - 1);
218
  }
219
  L->top--;
220
  lua_unlock(L);
221
}
222
 
223
 
224
LUA_API void lua_pushvalue (lua_State *L, int idx) {
225
  lua_lock(L);
226
  setobj2s(L, L->top, index2adr(L, idx));
227
  api_incr_top(L);
228
  lua_unlock(L);
229
}
230
 
231
 
232
 
233
/*
234
** access functions (stack -> C)
235
*/
236
 
237
 
238
LUA_API int lua_type (lua_State *L, int idx) {
239
  StkId o = index2adr(L, idx);
240
  return (o == luaO_nilobject) ? LUA_TNONE : ttype(o);
241
}
242
 
243
 
244
LUA_API const char *lua_typename (lua_State *L, int t) {
245
  UNUSED(L);
246
  return (t == LUA_TNONE) ? "no value" : luaT_typenames[t];
247
}
248
 
249
 
250
LUA_API int lua_iscfunction (lua_State *L, int idx) {
251
  StkId o = index2adr(L, idx);
252
  return iscfunction(o);
253
}
254
 
255
 
256
LUA_API int lua_isnumber (lua_State *L, int idx) {
257
  TValue n;
258
  const TValue *o = index2adr(L, idx);
259
  return tonumber(o, &n);
260
}
261
 
262
 
263
LUA_API int lua_isstring (lua_State *L, int idx) {
264
  int t = lua_type(L, idx);
265
  return (t == LUA_TSTRING || t == LUA_TNUMBER);
266
}
267
 
268
 
269
LUA_API int lua_isuserdata (lua_State *L, int idx) {
270
  const TValue *o = index2adr(L, idx);
271
  return (ttisuserdata(o) || ttislightuserdata(o));
272
}
273
 
274
 
275
LUA_API int lua_rawequal (lua_State *L, int index1, int index2) {
276
  StkId o1 = index2adr(L, index1);
277
  StkId o2 = index2adr(L, index2);
278
  return (o1 == luaO_nilobject || o2 == luaO_nilobject) ? 0
279
         : luaO_rawequalObj(o1, o2);
280
}
281
 
282
 
283
LUA_API int lua_equal (lua_State *L, int index1, int index2) {
284
  StkId o1, o2;
285
  int i;
286
  lua_lock(L);  /* may call tag method */
287
  o1 = index2adr(L, index1);
288
  o2 = index2adr(L, index2);
289
  i = (o1 == luaO_nilobject || o2 == luaO_nilobject) ? 0 : equalobj(L, o1, o2);
290
  lua_unlock(L);
291
  return i;
292
}
293
 
294
 
295
LUA_API int lua_lessthan (lua_State *L, int index1, int index2) {
296
  StkId o1, o2;
297
  int i;
298
  lua_lock(L);  /* may call tag method */
299
  o1 = index2adr(L, index1);
300
  o2 = index2adr(L, index2);
301
  i = (o1 == luaO_nilobject || o2 == luaO_nilobject) ? 0
302
       : luaV_lessthan(L, o1, o2);
303
  lua_unlock(L);
304
  return i;
305
}
306
 
307
 
308
 
309
LUA_API lua_Number lua_tonumber (lua_State *L, int idx) {
310
  TValue n;
311
  const TValue *o = index2adr(L, idx);
312
  if (tonumber(o, &n))
313
    return nvalue(o);
314
  else
315
    return 0;
316
}
317
 
318
 
319
LUA_API lua_Integer lua_tointeger (lua_State *L, int idx) {
320
  TValue n;
321
  const TValue *o = index2adr(L, idx);
322
  if (tonumber(o, &n)) {
323
    lua_Integer res;
324
    lua_Number num = nvalue(o);
325
    lua_number2integer(res, num);
326
    return res;
327
  }
328
  else
329
    return 0;
330
}
331
 
332
 
333
LUA_API int lua_toboolean (lua_State *L, int idx) {
334
  const TValue *o = index2adr(L, idx);
335
  return !l_isfalse(o);
336
}
337
 
338
 
339
LUA_API const char *lua_tolstring (lua_State *L, int idx, size_t *len) {
340
  StkId o = index2adr(L, idx);
341
  if (!ttisstring(o)) {
342
    lua_lock(L);  /* `luaV_tostring' may create a new string */
343
    if (!luaV_tostring(L, o)) {  /* conversion failed? */
344
      if (len != NULL) *len = 0;
345
      lua_unlock(L);
346
      return NULL;
347
    }
348
    luaC_checkGC(L);
349
    o = index2adr(L, idx);  /* previous call may reallocate the stack */
350
    lua_unlock(L);
351
  }
352
  if (len != NULL) *len = tsvalue(o)->len;
353
  return svalue(o);
354
}
355
 
356
 
357
LUA_API size_t lua_objlen (lua_State *L, int idx) {
358
  StkId o = index2adr(L, idx);
359
  switch (ttype(o)) {
360
    case LUA_TSTRING: return tsvalue(o)->len;
361
    case LUA_TUSERDATA: return uvalue(o)->len;
362
    case LUA_TTABLE: return luaH_getn(hvalue(o));
363
    case LUA_TNUMBER: {
364
      size_t l;
365
      lua_lock(L);  /* `luaV_tostring' may create a new string */
366
      l = (luaV_tostring(L, o) ? tsvalue(o)->len : 0);
367
      lua_unlock(L);
368
      return l;
369
    }
370
    default: return 0;
371
  }
372
}
373
 
374
 
375
LUA_API lua_CFunction lua_tocfunction (lua_State *L, int idx) {
376
  StkId o = index2adr(L, idx);
377
  return (!iscfunction(o)) ? NULL : clvalue(o)->c.f;
378
}
379
 
380
 
381
LUA_API void *lua_touserdata (lua_State *L, int idx) {
382
  StkId o = index2adr(L, idx);
383
  switch (ttype(o)) {
384
    case LUA_TUSERDATA: return (rawuvalue(o) + 1);
385
    case LUA_TLIGHTUSERDATA: return pvalue(o);
386
    default: return NULL;
387
  }
388
}
389
 
390
 
391
LUA_API lua_State *lua_tothread (lua_State *L, int idx) {
392
  StkId o = index2adr(L, idx);
393
  return (!ttisthread(o)) ? NULL : thvalue(o);
394
}
395
 
396
 
397
LUA_API const void *lua_topointer (lua_State *L, int idx) {
398
  StkId o = index2adr(L, idx);
399
  switch (ttype(o)) {
400
    case LUA_TTABLE: return hvalue(o);
401
    case LUA_TFUNCTION: return clvalue(o);
402
    case LUA_TTHREAD: return thvalue(o);
403
    case LUA_TUSERDATA:
404
    case LUA_TLIGHTUSERDATA:
405
      return lua_touserdata(L, idx);
406
    default: return NULL;
407
  }
408
}
409
 
410
 
411
 
412
/*
413
** push functions (C -> stack)
414
*/
415
 
416
 
417
LUA_API void lua_pushnil (lua_State *L) {
418
  lua_lock(L);
419
  setnilvalue(L->top);
420
  api_incr_top(L);
421
  lua_unlock(L);
422
}
423
 
424
 
425
LUA_API void lua_pushnumber (lua_State *L, lua_Number n) {
426
  lua_lock(L);
427
  setnvalue(L->top, n);
428
  api_incr_top(L);
429
  lua_unlock(L);
430
}
431
 
432
 
433
LUA_API void lua_pushinteger (lua_State *L, lua_Integer n) {
434
  lua_lock(L);
435
  setnvalue(L->top, cast_num(n));
436
  api_incr_top(L);
437
  lua_unlock(L);
438
}
439
 
440
 
441
LUA_API void lua_pushlstring (lua_State *L, const char *s, size_t len) {
442
  lua_lock(L);
443
  luaC_checkGC(L);
444
  setsvalue2s(L, L->top, luaS_newlstr(L, s, len));
445
  api_incr_top(L);
446
  lua_unlock(L);
447
}
448
 
449
 
450
LUA_API void lua_pushstring (lua_State *L, const char *s) {
451
  if (s == NULL)
452
    lua_pushnil(L);
453
  else
454
    lua_pushlstring(L, s, strlen(s));
455
}
456
 
457
 
458
LUA_API const char *lua_pushvfstring (lua_State *L, const char *fmt,
459
                                      va_list argp) {
460
  const char *ret;
461
  lua_lock(L);
462
  luaC_checkGC(L);
463
  ret = luaO_pushvfstring(L, fmt, argp);
464
  lua_unlock(L);
465
  return ret;
466
}
467
 
468
 
469
LUA_API const char *lua_pushfstring (lua_State *L, const char *fmt, ...) {
470
  const char *ret;
471
  va_list argp;
472
  lua_lock(L);
473
  luaC_checkGC(L);
474
  va_start(argp, fmt);
475
  ret = luaO_pushvfstring(L, fmt, argp);
476
  va_end(argp);
477
  lua_unlock(L);
478
  return ret;
479
}
480
 
481
 
482
LUA_API void lua_pushcclosure (lua_State *L, lua_CFunction fn, int n) {
483
  Closure *cl;
484
  lua_lock(L);
485
  luaC_checkGC(L);
486
  api_checknelems(L, n);
487
  cl = luaF_newCclosure(L, n, getcurrenv(L));
488
  cl->c.f = fn;
489
  L->top -= n;
490
  while (n--)
491
    setobj2n(L, &cl->c.upvalue[n], L->top+n);
492
  setclvalue(L, L->top, cl);
493
  lua_assert(iswhite(obj2gco(cl)));
494
  api_incr_top(L);
495
  lua_unlock(L);
496
}
497
 
498
 
499
LUA_API void lua_pushboolean (lua_State *L, int b) {
500
  lua_lock(L);
501
  setbvalue(L->top, (b != 0));  /* ensure that true is 1 */
502
  api_incr_top(L);
503
  lua_unlock(L);
504
}
505
 
506
 
507
LUA_API void lua_pushlightuserdata (lua_State *L, void *p) {
508
  lua_lock(L);
509
  setpvalue(L->top, p);
510
  api_incr_top(L);
511
  lua_unlock(L);
512
}
513
 
514
 
515
LUA_API int lua_pushthread (lua_State *L) {
516
  lua_lock(L);
517
  setthvalue(L, L->top, L);
518
  api_incr_top(L);
519
  lua_unlock(L);
520
  return (G(L)->mainthread == L);
521
}
522
 
523
 
524
 
525
/*
526
** get functions (Lua -> stack)
527
*/
528
 
529
 
530
LUA_API void lua_gettable (lua_State *L, int idx) {
531
  StkId t;
532
  lua_lock(L);
533
  t = index2adr(L, idx);
534
  api_checkvalidindex(L, t);
535
  luaV_gettable(L, t, L->top - 1, L->top - 1);
536
  lua_unlock(L);
537
}
538
 
539
 
540
LUA_API void lua_getfield (lua_State *L, int idx, const char *k) {
541
  StkId t;
542
  TValue key;
543
  lua_lock(L);
544
  t = index2adr(L, idx);
545
  api_checkvalidindex(L, t);
546
  setsvalue(L, &key, luaS_new(L, k));
547
  luaV_gettable(L, t, &key, L->top);
548
  api_incr_top(L);
549
  lua_unlock(L);
550
}
551
 
552
 
553
LUA_API void lua_rawget (lua_State *L, int idx) {
554
  StkId t;
555
  lua_lock(L);
556
  t = index2adr(L, idx);
557
  api_check(L, ttistable(t));
558
  setobj2s(L, L->top - 1, luaH_get(hvalue(t), L->top - 1));
559
  lua_unlock(L);
560
}
561
 
562
 
563
LUA_API void lua_rawgeti (lua_State *L, int idx, int n) {
564
  StkId o;
565
  lua_lock(L);
566
  o = index2adr(L, idx);
567
  api_check(L, ttistable(o));
568
  setobj2s(L, L->top, luaH_getnum(hvalue(o), n));
569
  api_incr_top(L);
570
  lua_unlock(L);
571
}
572
 
573
 
574
LUA_API void lua_createtable (lua_State *L, int narray, int nrec) {
575
  lua_lock(L);
576
  luaC_checkGC(L);
577
  sethvalue(L, L->top, luaH_new(L, narray, nrec));
578
  api_incr_top(L);
579
  lua_unlock(L);
580
}
581
 
582
 
583
LUA_API int lua_getmetatable (lua_State *L, int objindex) {
584
  const TValue *obj;
585
  Table *mt = NULL;
586
  int res;
587
  lua_lock(L);
588
  obj = index2adr(L, objindex);
589
  switch (ttype(obj)) {
590
    case LUA_TTABLE:
591
      mt = hvalue(obj)->metatable;
592
      break;
593
    case LUA_TUSERDATA:
594
      mt = uvalue(obj)->metatable;
595
      break;
596
    default:
597
      mt = G(L)->mt[ttype(obj)];
598
      break;
599
  }
600
  if (mt == NULL)
601
    res = 0;
602
  else {
603
    sethvalue(L, L->top, mt);
604
    api_incr_top(L);
605
    res = 1;
606
  }
607
  lua_unlock(L);
608
  return res;
609
}
610
 
611
 
612
LUA_API void lua_getfenv (lua_State *L, int idx) {
613
  StkId o;
614
  lua_lock(L);
615
  o = index2adr(L, idx);
616
  api_checkvalidindex(L, o);
617
  switch (ttype(o)) {
618
    case LUA_TFUNCTION:
619
      sethvalue(L, L->top, clvalue(o)->c.env);
620
      break;
621
    case LUA_TUSERDATA:
622
      sethvalue(L, L->top, uvalue(o)->env);
623
      break;
624
    case LUA_TTHREAD:
625
      setobj2s(L, L->top,  gt(thvalue(o)));
626
      break;
627
    default:
628
      setnilvalue(L->top);
629
      break;
630
  }
631
  api_incr_top(L);
632
  lua_unlock(L);
633
}
634
 
635
 
636
/*
637
** set functions (stack -> Lua)
638
*/
639
 
640
 
641
LUA_API void lua_settable (lua_State *L, int idx) {
642
  StkId t;
643
  lua_lock(L);
644
  api_checknelems(L, 2);
645
  t = index2adr(L, idx);
646
  api_checkvalidindex(L, t);
647
  luaV_settable(L, t, L->top - 2, L->top - 1);
648
  L->top -= 2;  /* pop index and value */
649
  lua_unlock(L);
650
}
651
 
652
 
653
LUA_API void lua_setfield (lua_State *L, int idx, const char *k) {
654
  StkId t;
655
  TValue key;
656
  lua_lock(L);
657
  api_checknelems(L, 1);
658
  t = index2adr(L, idx);
659
  api_checkvalidindex(L, t);
660
  setsvalue(L, &key, luaS_new(L, k));
661
  luaV_settable(L, t, &key, L->top - 1);
662
  L->top--;  /* pop value */
663
  lua_unlock(L);
664
}
665
 
666
 
667
LUA_API void lua_rawset (lua_State *L, int idx) {
668
  StkId t;
669
  lua_lock(L);
670
  api_checknelems(L, 2);
671
  t = index2adr(L, idx);
672
  api_check(L, ttistable(t));
673
  setobj2t(L, luaH_set(L, hvalue(t), L->top-2), L->top-1);
674
  luaC_barriert(L, hvalue(t), L->top-1);
675
  L->top -= 2;
676
  lua_unlock(L);
677
}
678
 
679
 
680
LUA_API void lua_rawseti (lua_State *L, int idx, int n) {
681
  StkId o;
682
  lua_lock(L);
683
  api_checknelems(L, 1);
684
  o = index2adr(L, idx);
685
  api_check(L, ttistable(o));
686
  setobj2t(L, luaH_setnum(L, hvalue(o), n), L->top-1);
687
  luaC_barriert(L, hvalue(o), L->top-1);
688
  L->top--;
689
  lua_unlock(L);
690
}
691
 
692
 
693
LUA_API int lua_setmetatable (lua_State *L, int objindex) {
694
  TValue *obj;
695
  Table *mt;
696
  lua_lock(L);
697
  api_checknelems(L, 1);
698
  obj = index2adr(L, objindex);
699
  api_checkvalidindex(L, obj);
700
  if (ttisnil(L->top - 1))
701
    mt = NULL;
702
  else {
703
    api_check(L, ttistable(L->top - 1));
704
    mt = hvalue(L->top - 1);
705
  }
706
  switch (ttype(obj)) {
707
    case LUA_TTABLE: {
708
      hvalue(obj)->metatable = mt;
709
      if (mt)
710
        luaC_objbarriert(L, hvalue(obj), mt);
711
      break;
712
    }
713
    case LUA_TUSERDATA: {
714
      uvalue(obj)->metatable = mt;
715
      if (mt)
716
        luaC_objbarrier(L, rawuvalue(obj), mt);
717
      break;
718
    }
719
    default: {
720
      G(L)->mt[ttype(obj)] = mt;
721
      break;
722
    }
723
  }
724
  L->top--;
725
  lua_unlock(L);
726
  return 1;
727
}
728
 
729
 
730
LUA_API int lua_setfenv (lua_State *L, int idx) {
731
  StkId o;
732
  int res = 1;
733
  lua_lock(L);
734
  api_checknelems(L, 1);
735
  o = index2adr(L, idx);
736
  api_checkvalidindex(L, o);
737
  api_check(L, ttistable(L->top - 1));
738
  switch (ttype(o)) {
739
    case LUA_TFUNCTION:
740
      clvalue(o)->c.env = hvalue(L->top - 1);
741
      break;
742
    case LUA_TUSERDATA:
743
      uvalue(o)->env = hvalue(L->top - 1);
744
      break;
745
    case LUA_TTHREAD:
746
      sethvalue(L, gt(thvalue(o)), hvalue(L->top - 1));
747
      break;
748
    default:
749
      res = 0;
750
      break;
751
  }
752
  luaC_objbarrier(L, gcvalue(o), hvalue(L->top - 1));
753
  L->top--;
754
  lua_unlock(L);
755
  return res;
756
}
757
 
758
 
759
/*
760
** `load' and `call' functions (run Lua code)
761
*/
762
 
763
 
764
#define adjustresults(L,nres) \
765
    { if (nres == LUA_MULTRET && L->top >= L->ci->top) L->ci->top = L->top; }
766
 
767
 
768
#define checkresults(L,na,nr) \
769
     api_check(L, (nr) == LUA_MULTRET || (L->ci->top - L->top >= (nr) - (na)))
770
 
771
 
772
LUA_API void lua_call (lua_State *L, int nargs, int nresults) {
773
  StkId func;
774
  lua_lock(L);
775
  api_checknelems(L, nargs+1);
776
  checkresults(L, nargs, nresults);
777
  func = L->top - (nargs+1);
778
  luaD_call(L, func, nresults);
779
  adjustresults(L, nresults);
780
  lua_unlock(L);
781
}
782
 
783
 
784
 
785
/*
786
** Execute a protected call.
787
*/
788
struct CallS {  /* data to `f_call' */
789
  StkId func;
790
  int nresults;
791
};
792
 
793
 
794
static void f_call (lua_State *L, void *ud) {
795
  struct CallS *c = cast(struct CallS *, ud);
796
  luaD_call(L, c->func, c->nresults);
797
}
798
 
799
 
800
 
801
LUA_API int lua_pcall (lua_State *L, int nargs, int nresults, int errfunc) {
802
  struct CallS c;
803
  int status;
804
  ptrdiff_t func;
805
  lua_lock(L);
806
  api_checknelems(L, nargs+1);
807
  checkresults(L, nargs, nresults);
808
  if (errfunc == 0)
809
    func = 0;
810
  else {
811
    StkId o = index2adr(L, errfunc);
812
    api_checkvalidindex(L, o);
813
    func = savestack(L, o);
814
  }
815
  c.func = L->top - (nargs+1);  /* function to be called */
816
  c.nresults = nresults;
817
  status = luaD_pcall(L, f_call, &c, savestack(L, c.func), func);
818
  adjustresults(L, nresults);
819
  lua_unlock(L);
820
  return status;
821
}
822
 
823
 
824
/*
825
** Execute a protected C call.
826
*/
827
struct CCallS {  /* data to `f_Ccall' */
828
  lua_CFunction func;
829
  void *ud;
830
};
831
 
832
 
833
static void f_Ccall (lua_State *L, void *ud) {
834
  struct CCallS *c = cast(struct CCallS *, ud);
835
  Closure *cl;
836
  cl = luaF_newCclosure(L, 0, getcurrenv(L));
837
  cl->c.f = c->func;
838
  setclvalue(L, L->top, cl);  /* push function */
839
  api_incr_top(L);
840
  setpvalue(L->top, c->ud);  /* push only argument */
841
  api_incr_top(L);
842
  luaD_call(L, L->top - 2, 0);
843
}
844
 
845
 
846
LUA_API int lua_cpcall (lua_State *L, lua_CFunction func, void *ud) {
847
  struct CCallS c;
848
  int status;
849
  lua_lock(L);
850
  c.func = func;
851
  c.ud = ud;
852
  status = luaD_pcall(L, f_Ccall, &c, savestack(L, L->top), 0);
853
  lua_unlock(L);
854
  return status;
855
}
856
 
857
 
858
LUA_API int lua_load (lua_State *L, lua_Reader reader, void *data,
859
                      const char *chunkname) {
860
  ZIO z;
861
  int status;
862
  lua_lock(L);
863
  if (!chunkname) chunkname = "?";
864
  luaZ_init(L, &z, reader, data);
865
  status = luaD_protectedparser(L, &z, chunkname);
866
  lua_unlock(L);
867
  return status;
868
}
869
 
870
 
871
LUA_API int lua_dump (lua_State *L, lua_Writer writer, void *data) {
872
  int status;
873
  TValue *o;
874
  lua_lock(L);
875
  api_checknelems(L, 1);
876
  o = L->top - 1;
877
  if (isLfunction(o))
878
    status = luaU_dump(L, clvalue(o)->l.p, writer, data, 0);
879
  else
880
    status = 1;
881
  lua_unlock(L);
882
  return status;
883
}
884
 
885
 
886
LUA_API int  lua_status (lua_State *L) {
887
  return L->status;
888
}
889
 
890
 
891
/*
892
** Garbage-collection function
893
*/
894
 
895
LUA_API int lua_gc (lua_State *L, int what, int data) {
896
  int res = 0;
897
  global_State *g;
898
  lua_lock(L);
899
  g = G(L);
900
  switch (what) {
901
    case LUA_GCSTOP: {
902
      g->GCthreshold = MAX_LUMEM;
903
      break;
904
    }
905
    case LUA_GCRESTART: {
906
      g->GCthreshold = g->totalbytes;
907
      break;
908
    }
909
    case LUA_GCCOLLECT: {
910
      luaC_fullgc(L);
911
      break;
912
    }
913
    case LUA_GCCOUNT: {
914
      /* GC values are expressed in Kbytes: #bytes/2^10 */
915
      res = cast_int(g->totalbytes >> 10);
916
      break;
917
    }
918
    case LUA_GCCOUNTB: {
919
      res = cast_int(g->totalbytes & 0x3ff);
920
      break;
921
    }
922
    case LUA_GCSTEP: {
923
      lu_mem a = (cast(lu_mem, data) << 10);
924
      if (a <= g->totalbytes)
925
        g->GCthreshold = g->totalbytes - a;
926
      else
927
        g->GCthreshold = 0;
928
      while (g->GCthreshold <= g->totalbytes)
929
        luaC_step(L);
930
      if (g->gcstate == GCSpause)  /* end of cycle? */
931
        res = 1;  /* signal it */
932
      break;
933
    }
934
    case LUA_GCSETPAUSE: {
935
      res = g->gcpause;
936
      g->gcpause = data;
937
      break;
938
    }
939
    case LUA_GCSETSTEPMUL: {
940
      res = g->gcstepmul;
941
      g->gcstepmul = data;
942
      break;
943
    }
944
    default: res = -1;  /* invalid option */
945
  }
946
  lua_unlock(L);
947
  return res;
948
}
949
 
950
 
951
 
952
/*
953
** miscellaneous functions
954
*/
955
 
956
 
957
LUA_API int lua_error (lua_State *L) {
958
  lua_lock(L);
959
  api_checknelems(L, 1);
960
  luaG_errormsg(L);
961
  lua_unlock(L);
962
  return 0;  /* to avoid warnings */
963
}
964
 
965
 
966
LUA_API int lua_next (lua_State *L, int idx) {
967
  StkId t;
968
  int more;
969
  lua_lock(L);
970
  t = index2adr(L, idx);
971
  api_check(L, ttistable(t));
972
  more = luaH_next(L, hvalue(t), L->top - 1);
973
  if (more) {
974
    api_incr_top(L);
975
  }
976
  else  /* no more elements */
977
    L->top -= 1;  /* remove key */
978
  lua_unlock(L);
979
  return more;
980
}
981
 
982
 
983
LUA_API void lua_concat (lua_State *L, int n) {
984
  lua_lock(L);
985
  api_checknelems(L, n);
986
  if (n >= 2) {
987
    luaC_checkGC(L);
988
    luaV_concat(L, n, cast_int(L->top - L->base) - 1);
989
    L->top -= (n-1);
990
  }
991
  else if (n == 0) {  /* push empty string */
992
    setsvalue2s(L, L->top, luaS_newlstr(L, "", 0));
993
    api_incr_top(L);
994
  }
995
  /* else n == 1; nothing to do */
996
  lua_unlock(L);
997
}
998
 
999
 
1000
LUA_API lua_Alloc lua_getallocf (lua_State *L, void **ud) {
1001
  lua_Alloc f;
1002
  lua_lock(L);
1003
  if (ud) *ud = G(L)->ud;
1004
  f = G(L)->frealloc;
1005
  lua_unlock(L);
1006
  return f;
1007
}
1008
 
1009
 
1010
LUA_API void lua_setallocf (lua_State *L, lua_Alloc f, void *ud) {
1011
  lua_lock(L);
1012
  G(L)->ud = ud;
1013
  G(L)->frealloc = f;
1014
  lua_unlock(L);
1015
}
1016
 
1017
 
1018
LUA_API void *lua_newuserdata (lua_State *L, size_t size) {
1019
  Udata *u;
1020
  lua_lock(L);
1021
  luaC_checkGC(L);
1022
  u = luaS_newudata(L, size, getcurrenv(L));
1023
  setuvalue(L, L->top, u);
1024
  api_incr_top(L);
1025
  lua_unlock(L);
1026
  return u + 1;
1027
}
1028
 
1029
 
1030
 
1031
 
1032
static const char *aux_upvalue (StkId fi, int n, TValue **val) {
1033
  Closure *f;
1034
  if (!ttisfunction(fi)) return NULL;
1035
  f = clvalue(fi);
1036
  if (f->c.isC) {
1037
    if (!(1 <= n && n <= f->c.nupvalues)) return NULL;
1038
    *val = &f->c.upvalue[n-1];
1039
    return "";
1040
  }
1041
  else {
1042
    Proto *p = f->l.p;
1043
    if (!(1 <= n && n <= p->sizeupvalues)) return NULL;
1044
    *val = f->l.upvals[n-1]->v;
1045
    return getstr(p->upvalues[n-1]);
1046
  }
1047
}
1048
 
1049
 
1050
LUA_API const char *lua_getupvalue (lua_State *L, int funcindex, int n) {
1051
  const char *name;
1052
  TValue *val;
1053
  lua_lock(L);
1054
  name = aux_upvalue(index2adr(L, funcindex), n, &val);
1055
  if (name) {
1056
    setobj2s(L, L->top, val);
1057
    api_incr_top(L);
1058
  }
1059
  lua_unlock(L);
1060
  return name;
1061
}
1062
 
1063
 
1064
LUA_API const char *lua_setupvalue (lua_State *L, int funcindex, int n) {
1065
  const char *name;
1066
  TValue *val;
1067
  StkId fi;
1068
  lua_lock(L);
1069
  fi = index2adr(L, funcindex);
1070
  api_checknelems(L, 1);
1071
  name = aux_upvalue(fi, n, &val);
1072
  if (name) {
1073
    L->top--;
1074
    setobj(L, val, L->top);
1075
    luaC_barrier(L, clvalue(fi), L->top);
1076
  }
1077
  lua_unlock(L);
1078
  return name;
1079
}
1080