summaryrefslogtreecommitdiff
path: root/lib/lua/src/lobject.c
diff options
context:
space:
mode:
Diffstat (limited to 'lib/lua/src/lobject.c')
-rw-r--r--lib/lua/src/lobject.c134
1 files changed, 75 insertions, 59 deletions
diff --git a/lib/lua/src/lobject.c b/lib/lua/src/lobject.c
index 62c70b6..0bfc9be 100644
--- a/lib/lua/src/lobject.c
+++ b/lib/lua/src/lobject.c
@@ -1,15 +1,17 @@
/*
-** $Id: lobject.c,v 1.6 2004-12-19 16:14:04 pixel Exp $
+** $Id: lobject.c,v 1.7 2007-07-27 10:05:54 pixel Exp $
** Some generic functions over Lua objects
** See Copyright Notice in lua.h
*/
#include <ctype.h>
#include <stdarg.h>
+#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define lobject_c
+#define LUA_CORE
#include "lua.h"
@@ -20,57 +22,60 @@
#include "lstring.h"
#include "lvm.h"
-const TObject luaO_nilobject = {LUA_TNIL, {NULL}};
+
+
+const TValue luaO_nilobject_ = {{NULL}, LUA_TNIL};
/*
** converts an integer to a "floating point byte", represented as
-** (mmmmmxxx), where the real value is (xxx) * 2^(mmmmm)
+** (eeeeexxx), where the real value is (1xxx) * 2^(eeeee - 1) if
+** eeeee != 0 and (xxx) otherwise.
*/
int luaO_int2fb (unsigned int x) {
- int m = 0; /* mantissa */
- while (x >= (1<<3)) {
+ int e = 0; /* expoent */
+ while (x >= 16) {
x = (x+1) >> 1;
- m++;
+ e++;
}
- return (m << 3) | cast(int, x);
+ if (x < 8) return x;
+ else return ((e+1) << 3) | (cast_int(x) - 8);
+}
+
+
+/* converts back */
+int luaO_fb2int (int x) {
+ int e = (x >> 3) & 31;
+ if (e == 0) return x;
+ else return ((x & 7)+8) << (e - 1);
}
int luaO_log2 (unsigned int x) {
- static const lu_byte log_8[255] = {
- 0,
- 1,1,
- 2,2,2,2,
- 3,3,3,3,3,3,3,3,
- 4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,
- 5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,
- 6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,
+ static const lu_byte log_2[256] = {
+ 0,1,2,2,3,3,3,3,4,4,4,4,4,4,4,4,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,
6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,
7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,
7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,
- 7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,
- 7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7
+ 8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,
+ 8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,
+ 8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,
+ 8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8,8
};
- if (x >= 0x00010000) {
- if (x >= 0x01000000) return log_8[((x>>24) & 0xff) - 1]+24;
- else return log_8[((x>>16) & 0xff) - 1]+16;
- }
- else {
- if (x >= 0x00000100) return log_8[((x>>8) & 0xff) - 1]+8;
- else if (x) return log_8[(x & 0xff) - 1];
- return -1; /* special `log' for 0 */
- }
+ int l = -1;
+ while (x >= 256) { l += 8; x >>= 8; }
+ return l + log_2[x];
+
}
-int luaO_rawequalObj (const TObject *t1, const TObject *t2) {
+int luaO_rawequalObj (const TValue *t1, const TValue *t2) {
if (ttype(t1) != ttype(t2)) return 0;
else switch (ttype(t1)) {
case LUA_TNIL:
return 1;
case LUA_TNUMBER:
- return nvalue(t1) == nvalue(t2);
+ return luai_numeq(nvalue(t1), nvalue(t2));
case LUA_TBOOLEAN:
return bvalue(t1) == bvalue(t2); /* boolean true must be 1 !! */
case LUA_TLIGHTUSERDATA:
@@ -84,45 +89,40 @@ int luaO_rawequalObj (const TObject *t1, const TObject *t2) {
int luaO_str2d (const char *s, lua_Number *result) {
char *endptr;
- size_t l = strlen(s);
- lua_Number res;
- if ((l > 0) && (s[0] == '0') && (s[1] != '.')) {
- if ((l > 2) && (s[1] == 'x')) {
- res = strtol(s + 2, &endptr, 16);
- } else {
- res = strtol(s + 1, &endptr, 8);
- }
- } else {
- res = strtod(s, &endptr);
- }
- if (endptr == s) return 0; /* no conversion */
- while (isspace((unsigned char)(*endptr))) endptr++;
+ *result = lua_str2number(s, &endptr);
+ if (endptr == s) return 0; /* conversion failed */
+ if (*endptr == 'x' || *endptr == 'X') /* maybe an hexadecimal constant? */
+ *result = cast_num(strtoul(s, &endptr, 16));
+ if (*endptr == '\0') return 1; /* most common case */
+ while (isspace(cast(unsigned char, *endptr))) endptr++;
if (*endptr != '\0') return 0; /* invalid trailing characters? */
- *result = res;
return 1;
}
static void pushstr (lua_State *L, const char *str) {
- setsvalue2s(L->top, luaS_new(L, str));
+ setsvalue2s(L, L->top, luaS_new(L, str));
incr_top(L);
}
-/* this function handles only `%d', `%c', %f, and `%s' formats */
+/* this function handles only `%d', `%c', %f, %p, and `%s' formats */
const char *luaO_pushvfstring (lua_State *L, const char *fmt, va_list argp) {
int n = 1;
pushstr(L, "");
for (;;) {
const char *e = strchr(fmt, '%');
if (e == NULL) break;
- setsvalue2s(L->top, luaS_newlstr(L, fmt, e-fmt));
+ setsvalue2s(L, L->top, luaS_newlstr(L, fmt, e-fmt));
incr_top(L);
switch (*(e+1)) {
- case 's':
- pushstr(L, va_arg(argp, char *));
+ case 's': {
+ const char *s = va_arg(argp, char *);
+ if (s == NULL) s = "(null)";
+ pushstr(L, s);
break;
+ }
case 'c': {
char buff[2];
buff[0] = cast(char, va_arg(argp, int));
@@ -130,24 +130,40 @@ const char *luaO_pushvfstring (lua_State *L, const char *fmt, va_list argp) {
pushstr(L, buff);
break;
}
- case 'd':
- setnvalue(L->top, cast(lua_Number, va_arg(argp, int)));
+ case 'd': {
+ setnvalue(L->top, cast_num(va_arg(argp, int)));
incr_top(L);
break;
- case 'f':
- setnvalue(L->top, cast(lua_Number, va_arg(argp, l_uacNumber)));
+ }
+ case 'f': {
+ setnvalue(L->top, cast_num(va_arg(argp, l_uacNumber)));
incr_top(L);
break;
- case '%':
+ }
+ case 'p': {
+ char buff[4*sizeof(void *) + 8]; /* should be enough space for a `%p' */
+ sprintf(buff, "%p", va_arg(argp, void *));
+ pushstr(L, buff);
+ break;
+ }
+ case '%': {
pushstr(L, "%");
break;
- default: lua_assert(0);
+ }
+ default: {
+ char buff[3];
+ buff[0] = '%';
+ buff[1] = *(e+1);
+ buff[2] = '\0';
+ pushstr(L, buff);
+ break;
+ }
}
n += 2;
fmt = e+2;
}
pushstr(L, fmt);
- luaV_concat(L, n+1, L->top - L->base - 1);
+ luaV_concat(L, n+1, cast_int(L->top - L->base) - 1);
L->top -= n;
return svalue(L->top - 1);
}
@@ -163,26 +179,26 @@ const char *luaO_pushfstring (lua_State *L, const char *fmt, ...) {
}
-void luaO_chunkid (char *out, const char *source, int bufflen) {
+void luaO_chunkid (char *out, const char *source, size_t bufflen) {
if (*source == '=') {
strncpy(out, source+1, bufflen); /* remove first char */
out[bufflen-1] = '\0'; /* ensures null termination */
}
else { /* out = "source", or "...source" */
if (*source == '@') {
- int l;
+ size_t l;
source++; /* skip the `@' */
- bufflen -= sizeof(" `...' ");
+ bufflen -= sizeof(" '...' ");
l = strlen(source);
strcpy(out, "");
- if (l>bufflen) {
+ if (l > bufflen) {
source += (l-bufflen); /* get last part of file name */
strcat(out, "...");
}
strcat(out, source);
}
else { /* out = [string "string"] */
- int len = strcspn(source, "\n"); /* stop at first newline */
+ size_t len = strcspn(source, "\n\r"); /* stop at first newline */
bufflen -= sizeof(" [string \"...\"] ");
if (len > bufflen) len = bufflen;
strcpy(out, "[string \"");