mirror of
https://github.com/ccxvii/mujs.git
synced 2026-02-06 09:51:41 +08:00
Put js_Object contents in a union.
This commit is contained in:
14
jsbboolean.c
14
jsbboolean.c
@@ -17,23 +17,23 @@ static int jsB_Boolean(js_State *J, int n)
|
||||
|
||||
static int Bp_toString(js_State *J, int n)
|
||||
{
|
||||
js_Object *T = js_toobject(J, 0);
|
||||
if (T->type != JS_CBOOLEAN) jsR_error(J, "TypeError");
|
||||
js_pushliteral(J, T->primitive.boolean ? "true" : "false");
|
||||
js_Object *self = js_toobject(J, 0);
|
||||
if (self->type != JS_CBOOLEAN) jsR_error(J, "TypeError");
|
||||
js_pushliteral(J, self->u.boolean ? "true" : "false");
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int Bp_valueOf(js_State *J, int n)
|
||||
{
|
||||
js_Object *T = js_toobject(J, 0);
|
||||
if (T->type != JS_CBOOLEAN) jsR_error(J, "TypeError");
|
||||
js_pushboolean(J, T->primitive.boolean);
|
||||
js_Object *self = js_toobject(J, 0);
|
||||
if (self->type != JS_CBOOLEAN) jsR_error(J, "TypeError");
|
||||
js_pushboolean(J, self->u.boolean);
|
||||
return 1;
|
||||
}
|
||||
|
||||
void jsB_initboolean(js_State *J)
|
||||
{
|
||||
J->Boolean_prototype->primitive.boolean = 0;
|
||||
J->Boolean_prototype->u.boolean = 0;
|
||||
|
||||
js_pushobject(J, jsR_newcconstructor(J, jsB_Boolean, jsB_new_Boolean));
|
||||
{
|
||||
|
||||
@@ -61,8 +61,8 @@ static int Fp_call(js_State *J, int n)
|
||||
|
||||
void jsB_initfunction(js_State *J)
|
||||
{
|
||||
J->Function_prototype->cfunction = jsB_Function_prototype;
|
||||
J->Function_prototype->cconstructor = NULL;
|
||||
J->Function_prototype->u.c.function = jsB_Function_prototype;
|
||||
J->Function_prototype->u.c.constructor = NULL;
|
||||
|
||||
js_pushobject(J, jsR_newcconstructor(J, jsB_Function, jsB_new_Function));
|
||||
{
|
||||
|
||||
32
jsbnumber.c
32
jsbnumber.c
@@ -17,27 +17,27 @@ static int jsB_Number(js_State *J, int n)
|
||||
|
||||
static int Np_valueOf(js_State *J, int n)
|
||||
{
|
||||
js_Object *T = js_toobject(J, 0);
|
||||
if (T->type != JS_CNUMBER) jsR_error(J, "TypeError");
|
||||
js_pushnumber(J, T->primitive.number);
|
||||
js_Object *self = js_toobject(J, 0);
|
||||
if (self->type != JS_CNUMBER) jsR_error(J, "TypeError");
|
||||
js_pushnumber(J, self->u.number);
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int Np_toString(js_State *J, int n)
|
||||
{
|
||||
js_Object *T = js_toobject(J, 0);
|
||||
if (T->type != JS_CNUMBER) jsR_error(J, "TypeError");
|
||||
js_pushliteral(J, jsR_numbertostring(J, T->primitive.number));
|
||||
js_Object *self = js_toobject(J, 0);
|
||||
if (self->type != JS_CNUMBER) jsR_error(J, "TypeError");
|
||||
js_pushliteral(J, jsR_numbertostring(J, self->u.number));
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int Np_toFixed(js_State *J, int n)
|
||||
{
|
||||
char buf[40];
|
||||
js_Object *T = js_toobject(J, 0);
|
||||
js_Object *self = js_toobject(J, 0);
|
||||
int width = js_tonumber(J, 1);
|
||||
if (T->type != JS_CNUMBER) jsR_error(J, "TypeError");
|
||||
sprintf(buf, "%*f", width, T->primitive.number);
|
||||
if (self->type != JS_CNUMBER) jsR_error(J, "TypeError");
|
||||
sprintf(buf, "%*f", width, self->u.number);
|
||||
js_pushstring(J, buf);
|
||||
return 1;
|
||||
}
|
||||
@@ -45,10 +45,10 @@ static int Np_toFixed(js_State *J, int n)
|
||||
static int Np_toExponential(js_State *J, int n)
|
||||
{
|
||||
char buf[40];
|
||||
js_Object *T = js_toobject(J, 0);
|
||||
js_Object *self = js_toobject(J, 0);
|
||||
int width = js_tonumber(J, 1);
|
||||
if (T->type != JS_CNUMBER) jsR_error(J, "TypeError");
|
||||
sprintf(buf, "%*e", width, T->primitive.number);
|
||||
if (self->type != JS_CNUMBER) jsR_error(J, "TypeError");
|
||||
sprintf(buf, "%*e", width, self->u.number);
|
||||
js_pushstring(J, buf);
|
||||
return 1;
|
||||
}
|
||||
@@ -56,17 +56,17 @@ static int Np_toExponential(js_State *J, int n)
|
||||
static int Np_toPrecision(js_State *J, int n)
|
||||
{
|
||||
char buf[40];
|
||||
js_Object *T = js_toobject(J, 0);
|
||||
js_Object *self = js_toobject(J, 0);
|
||||
int width = js_tonumber(J, 1);
|
||||
if (T->type != JS_CNUMBER) jsR_error(J, "TypeError");
|
||||
sprintf(buf, "%*g", width, T->primitive.number);
|
||||
if (self->type != JS_CNUMBER) jsR_error(J, "TypeError");
|
||||
sprintf(buf, "%*g", width, self->u.number);
|
||||
js_pushstring(J, buf);
|
||||
return 1;
|
||||
}
|
||||
|
||||
void jsB_initnumber(js_State *J)
|
||||
{
|
||||
J->Number_prototype->primitive.number = 0;
|
||||
J->Number_prototype->u.number = 0;
|
||||
|
||||
js_pushobject(J, jsR_newcconstructor(J, jsB_Number, jsB_new_Number));
|
||||
{
|
||||
|
||||
18
jsbobject.c
18
jsbobject.c
@@ -23,8 +23,8 @@ static int jsB_Object(js_State *J, int n)
|
||||
|
||||
static int Op_toString(js_State *J, int n)
|
||||
{
|
||||
js_Object *T = js_toobject(J, 0);
|
||||
switch (T->type) {
|
||||
js_Object *self = js_toobject(J, 0);
|
||||
switch (self->type) {
|
||||
case JS_COBJECT: js_pushliteral(J, "[object Object]"); break;
|
||||
case JS_CARRAY: js_pushliteral(J, "[object Array]"); break;
|
||||
case JS_CFUNCTION: js_pushliteral(J, "[object Function]"); break;
|
||||
@@ -50,21 +50,21 @@ static int Op_valueOf(js_State *J, int n)
|
||||
|
||||
static int Op_hasOwnProperty(js_State *J, int n)
|
||||
{
|
||||
js_Object *T = js_toobject(J, 0);
|
||||
js_Object *self = js_toobject(J, 0);
|
||||
const char *name = js_tostring(J, 1);
|
||||
js_Property *ref = jsR_getownproperty(J, T, name);
|
||||
js_Property *ref = jsR_getownproperty(J, self, name);
|
||||
js_pushboolean(J, ref != NULL);
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int Op_isPrototypeOf(js_State *J, int n)
|
||||
{
|
||||
js_Object *T = js_toobject(J, 0);
|
||||
js_Object *self = js_toobject(J, 0);
|
||||
if (js_isobject(J, 1)) {
|
||||
js_Object *V = js_toobject(J, 1);
|
||||
do {
|
||||
V = V->prototype;
|
||||
if (V == T) {
|
||||
if (V == self) {
|
||||
js_pushboolean(J, 1);
|
||||
return 1;
|
||||
}
|
||||
@@ -76,10 +76,10 @@ static int Op_isPrototypeOf(js_State *J, int n)
|
||||
|
||||
static int Op_propertyIsEnumerable(js_State *J, int n)
|
||||
{
|
||||
js_Object *T = js_toobject(J, 0);
|
||||
js_Object *self = js_toobject(J, 0);
|
||||
const char *name = js_tostring(J, 1);
|
||||
js_Property *ref = jsR_getownproperty(J, T, name);
|
||||
js_pushboolean(J, ref && (ref->flags & JS_PENUMERABLE));
|
||||
js_Property *ref = jsR_getownproperty(J, self, name);
|
||||
js_pushboolean(J, ref && !ref->dontenum);
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
||||
14
jsbstring.c
14
jsbstring.c
@@ -18,17 +18,17 @@ static int jsB_String(js_State *J, int n)
|
||||
|
||||
static int Sp_toString(js_State *J, int n)
|
||||
{
|
||||
js_Object *T = js_toobject(J, 0);
|
||||
if (T->type != JS_CSTRING) jsR_error(J, "TypeError");
|
||||
js_pushliteral(J, T->primitive.string);
|
||||
js_Object *self = js_toobject(J, 0);
|
||||
if (self->type != JS_CSTRING) jsR_error(J, "TypeError");
|
||||
js_pushliteral(J, self->u.string);
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int Sp_valueOf(js_State *J, int n)
|
||||
{
|
||||
js_Object *T = js_toobject(J, 0);
|
||||
if (T->type != JS_CSTRING) jsR_error(J, "TypeError");
|
||||
js_pushliteral(J, T->primitive.string);
|
||||
js_Object *self = js_toobject(J, 0);
|
||||
if (self->type != JS_CSTRING) jsR_error(J, "TypeError");
|
||||
js_pushliteral(J, self->u.string);
|
||||
return 1;
|
||||
}
|
||||
|
||||
@@ -50,7 +50,7 @@ static int S_fromCharCode(js_State *J, int n)
|
||||
|
||||
void jsB_initstring(js_State *J)
|
||||
{
|
||||
J->String_prototype->primitive.string = "";
|
||||
J->String_prototype->u.string = "";
|
||||
|
||||
js_pushobject(J, jsR_newcconstructor(J, jsB_String, jsB_new_String));
|
||||
{
|
||||
|
||||
16
jsdump.c
16
jsdump.c
@@ -674,15 +674,15 @@ void js_dumpvalue(js_State *J, js_Value v)
|
||||
case JS_CFUNCTION:
|
||||
printf("function(%p, %s, %s:%d)",
|
||||
v.u.object,
|
||||
v.u.object->function->name,
|
||||
v.u.object->function->filename,
|
||||
v.u.object->function->line);
|
||||
v.u.object->u.f.function->name,
|
||||
v.u.object->u.f.function->filename,
|
||||
v.u.object->u.f.function->line);
|
||||
break;
|
||||
case JS_CSCRIPT: printf("script(%s)", v.u.object->function->filename); break;
|
||||
case JS_CCFUNCTION: printf("cfunction(%p)", v.u.object->cfunction); break;
|
||||
case JS_CBOOLEAN: printf("boolean(%d)", v.u.object->primitive.boolean); break;
|
||||
case JS_CNUMBER: printf("number(%g)", v.u.object->primitive.number); break;
|
||||
case JS_CSTRING: printf("string('%s')", v.u.object->primitive.string); break;
|
||||
case JS_CSCRIPT: printf("script(%s)", v.u.object->u.f.function->filename); break;
|
||||
case JS_CCFUNCTION: printf("cfunction(%p)", v.u.object->u.c.function); break;
|
||||
case JS_CBOOLEAN: printf("boolean(%d)", v.u.object->u.boolean); break;
|
||||
case JS_CNUMBER: printf("number(%g)", v.u.object->u.number); break;
|
||||
case JS_CSTRING: printf("string('%s')", v.u.object->u.string); break;
|
||||
default: printf("<unknown %p>", v.u.object); break;
|
||||
}
|
||||
break;
|
||||
|
||||
10
jsgc.c
10
jsgc.c
@@ -69,10 +69,12 @@ static void jsG_markobject(js_State *J, int mark, js_Object *obj)
|
||||
jsG_markproperty(J, mark, obj->properties);
|
||||
if (obj->prototype && obj->prototype->gcmark != mark)
|
||||
jsG_markobject(J, mark, obj->prototype);
|
||||
if (obj->scope && obj->scope->gcmark != mark)
|
||||
jsG_markenvironment(J, mark, obj->scope);
|
||||
if (obj->function && obj->function->gcmark != mark)
|
||||
jsG_markfunction(J, mark, obj->function);
|
||||
if (obj->type == JS_CFUNCTION || obj->type == JS_CSCRIPT) {
|
||||
if (obj->u.f.scope && obj->u.f.scope->gcmark != mark)
|
||||
jsG_markenvironment(J, mark, obj->u.f.scope);
|
||||
if (obj->u.f.function && obj->u.f.function->gcmark != mark)
|
||||
jsG_markfunction(J, mark, obj->u.f.function);
|
||||
}
|
||||
}
|
||||
|
||||
static void jsG_markstack(js_State *J, int mark)
|
||||
|
||||
21
jsobject.c
21
jsobject.c
@@ -7,52 +7,53 @@
|
||||
static js_Object *jsR_newfunction(js_State *J, js_Function *function, js_Environment *scope)
|
||||
{
|
||||
js_Object *obj = jsR_newobject(J, JS_CFUNCTION, J->Function_prototype);
|
||||
obj->function = function;
|
||||
obj->scope = scope;
|
||||
obj->u.f.function = function;
|
||||
obj->u.f.scope = scope;
|
||||
return obj;
|
||||
}
|
||||
|
||||
static js_Object *jsR_newscript(js_State *J, js_Function *function)
|
||||
{
|
||||
js_Object *obj = jsR_newobject(J, JS_CSCRIPT, NULL);
|
||||
obj->function = function;
|
||||
obj->u.f.function = function;
|
||||
obj->u.f.scope = NULL;
|
||||
return obj;
|
||||
}
|
||||
|
||||
static js_Object *jsR_newcfunction(js_State *J, js_CFunction cfunction)
|
||||
{
|
||||
js_Object *obj = jsR_newobject(J, JS_CCFUNCTION, J->Function_prototype);
|
||||
obj->cfunction = cfunction;
|
||||
obj->cconstructor = NULL;
|
||||
obj->u.c.function = cfunction;
|
||||
obj->u.c.constructor = NULL;
|
||||
return obj;
|
||||
}
|
||||
|
||||
js_Object *jsR_newcconstructor(js_State *J, js_CFunction cfunction, js_CFunction cconstructor)
|
||||
{
|
||||
js_Object *obj = jsR_newobject(J, JS_CCFUNCTION, J->Function_prototype);
|
||||
obj->cfunction = cfunction;
|
||||
obj->cconstructor = cconstructor;
|
||||
obj->u.c.function = cfunction;
|
||||
obj->u.c.constructor = cconstructor;
|
||||
return obj;
|
||||
}
|
||||
|
||||
js_Object *jsR_newboolean(js_State *J, int v)
|
||||
{
|
||||
js_Object *obj = jsR_newobject(J, JS_CBOOLEAN, J->Boolean_prototype);
|
||||
obj->primitive.boolean = v;
|
||||
obj->u.boolean = v;
|
||||
return obj;
|
||||
}
|
||||
|
||||
js_Object *jsR_newnumber(js_State *J, double v)
|
||||
{
|
||||
js_Object *obj = jsR_newobject(J, JS_CNUMBER, J->Number_prototype);
|
||||
obj->primitive.number = v;
|
||||
obj->u.number = v;
|
||||
return obj;
|
||||
}
|
||||
|
||||
js_Object *jsR_newstring(js_State *J, const char *v)
|
||||
{
|
||||
js_Object *obj = jsR_newobject(J, JS_CSTRING, J->String_prototype);
|
||||
obj->primitive.string = v;
|
||||
obj->u.string = v;
|
||||
return obj;
|
||||
}
|
||||
|
||||
|
||||
23
jsobject.h
23
jsobject.h
@@ -31,12 +31,6 @@ enum js_Class {
|
||||
JS_CMATH,
|
||||
};
|
||||
|
||||
enum {
|
||||
JS_PWRITABLE = 1,
|
||||
JS_PENUMERABLE = 2,
|
||||
JS_PCONFIGURABLE = 4,
|
||||
};
|
||||
|
||||
enum {
|
||||
JS_HNONE,
|
||||
JS_HNUMBER,
|
||||
@@ -63,12 +57,15 @@ struct js_Object
|
||||
int boolean;
|
||||
double number;
|
||||
const char *string;
|
||||
} primitive;
|
||||
js_Environment *scope;
|
||||
js_Function *function;
|
||||
js_CFunction cfunction;
|
||||
js_CFunction cconstructor;
|
||||
|
||||
struct {
|
||||
js_Function *function;
|
||||
js_Environment *scope;
|
||||
} f;
|
||||
struct {
|
||||
js_CFunction function;
|
||||
js_CFunction constructor;
|
||||
} c;
|
||||
} u;
|
||||
js_Object *gcnext;
|
||||
int gcmark;
|
||||
};
|
||||
@@ -78,8 +75,8 @@ struct js_Property
|
||||
const char *name;
|
||||
js_Property *left, *right;
|
||||
int level;
|
||||
unsigned short readonly, dontenum, dontconf;
|
||||
js_Value value;
|
||||
int flags;
|
||||
};
|
||||
|
||||
/* jsvalue.c */
|
||||
|
||||
10
jsproperty.c
10
jsproperty.c
@@ -27,9 +27,11 @@ static js_Property *newproperty(js_State *J, const char *name)
|
||||
node->name = js_intern(J, name);
|
||||
node->left = node->right = &sentinel;
|
||||
node->level = 1;
|
||||
node->readonly = 0;
|
||||
node->dontenum = 0;
|
||||
node->dontconf = 0;
|
||||
node->value.type = JS_TUNDEFINED;
|
||||
node->value.u.number = 0;
|
||||
node->flags = 0;
|
||||
return node;
|
||||
}
|
||||
|
||||
@@ -132,7 +134,7 @@ found:
|
||||
|
||||
js_Object *jsR_newobject(js_State *J, js_Class type, js_Object *prototype)
|
||||
{
|
||||
js_Object *obj = malloc(sizeof(js_Object));
|
||||
js_Object *obj = calloc(sizeof(js_Object), 1);
|
||||
obj->gcmark = 0;
|
||||
obj->gcnext = J->gcobj;
|
||||
J->gcobj = obj;
|
||||
@@ -141,10 +143,6 @@ js_Object *jsR_newobject(js_State *J, js_Class type, js_Object *prototype)
|
||||
obj->type = type;
|
||||
obj->properties = &sentinel;
|
||||
obj->prototype = prototype;
|
||||
obj->primitive.number = 0;
|
||||
obj->scope = NULL;
|
||||
obj->function = NULL;
|
||||
obj->cfunction = NULL;
|
||||
return obj;
|
||||
}
|
||||
|
||||
|
||||
14
jsrun.c
14
jsrun.c
@@ -393,11 +393,11 @@ void js_call(js_State *J, int n)
|
||||
int savebot = BOT;
|
||||
BOT = TOP - n - 1;
|
||||
if (obj->type == JS_CFUNCTION)
|
||||
jsR_callfunction(J, n, obj->function, obj->scope);
|
||||
jsR_callfunction(J, n, obj->u.f.function, obj->u.f.scope);
|
||||
else if (obj->type == JS_CSCRIPT)
|
||||
jsR_callscript(J, n, obj->function);
|
||||
jsR_callscript(J, n, obj->u.f.function);
|
||||
else if (obj->type == JS_CCFUNCTION)
|
||||
jsR_callcfunction(J, n, obj->cfunction);
|
||||
jsR_callcfunction(J, n, obj->u.c.function);
|
||||
else
|
||||
jsR_error(J, "TypeError (not a function)");
|
||||
BOT = savebot;
|
||||
@@ -409,10 +409,10 @@ void js_construct(js_State *J, int n)
|
||||
js_Object *prototype;
|
||||
|
||||
/* built-in constructors create their own objects */
|
||||
if (obj->type == JS_CCFUNCTION && obj->cconstructor) {
|
||||
if (obj->type == JS_CCFUNCTION && obj->u.c.constructor) {
|
||||
int savebot = BOT;
|
||||
BOT = TOP - n;
|
||||
jsR_callcfunction(J, n, obj->cconstructor);
|
||||
jsR_callcfunction(J, n, obj->u.c.constructor);
|
||||
BOT = savebot;
|
||||
return;
|
||||
}
|
||||
@@ -459,8 +459,8 @@ void jsR_dumpenvironment(js_State *J, js_Environment *E, int d)
|
||||
|
||||
void js_trap(js_State *J, int pc)
|
||||
{
|
||||
fprintf(stderr, "trap at %d in ", pc);
|
||||
js_Function *F = STACK[BOT-1].u.object->function;
|
||||
js_Function *F = STACK[BOT-1].u.object->u.f.function;
|
||||
printf("trap at %d in ", pc);
|
||||
jsC_dumpfunction(J, F);
|
||||
jsR_dumpstack(J);
|
||||
jsR_dumpenvironment(J, J->E, 0);
|
||||
|
||||
Reference in New Issue
Block a user