1. Replacing IdScriptableObject.wrap_* methods by their ScriptRuntime.wrap* counterparts since the wrap methods are useful not only for subclasses of IdScriptableObject.

2. Reorganizing execIdCall in few classes inherited from IdScriptableObject to shrink code size.
This commit is contained in:
igor%mir2.org 2004-09-10 18:02:06 +00:00
Родитель 5eff6a3a6f
Коммит 985134c0ed
14 изменённых файлов: 184 добавлений и 198 удалений

Просмотреть файл

@ -50,47 +50,47 @@ public class Control {
* Then set up the execution environment and begin to
* execute scripts.
*/
public static void main(String[] args)
{
public static void main(String[] args)
{
Context cx = Context.enter();
try {
// Set version to JavaScript1.2 so that we get object-literal style
// printing instead of "[object Object]"
cx.setLanguageVersion(Context.VERSION_1_2);
try {
// Set version to JavaScript1.2 so that we get object-literal style
// printing instead of "[object Object]"
cx.setLanguageVersion(Context.VERSION_1_2);
// Initialize the standard objects (Object, Function, etc.)
// This must be done before scripts can be executed.
Scriptable scope = cx.initStandardObjects();
// Initialize the standard objects (Object, Function, etc.)
// This must be done before scripts can be executed.
Scriptable scope = cx.initStandardObjects();
// Now we can evaluate a script. Let's create a new object
// using the object literal notation.
Object result = cx.evaluateString(scope, "obj = {a:1, b:['x','y']}",
"MySource", 1, null);
// Now we can evaluate a script. Let's create a new object
// using the object literal notation.
Object result = cx.evaluateString(scope, "obj = {a:1, b:['x','y']}",
"MySource", 1, null);
Scriptable obj = (Scriptable) scope.get("obj", scope);
Scriptable obj = (Scriptable) scope.get("obj", scope);
// Should print "obj == result" (Since the result of an assignment
// expression is the value that was assigned)
System.out.println("obj " + (obj == result ? "==" : "!=") +
" result");
// Should print "obj == result" (Since the result of an assignment
// expression is the value that was assigned)
System.out.println("obj " + (obj == result ? "==" : "!=") +
" result");
// Should print "obj.a == 1"
System.out.println("obj.a == " + obj.get("a", obj));
// Should print "obj.a == 1"
System.out.println("obj.a == " + obj.get("a", obj));
Scriptable b = (Scriptable) obj.get("b", obj);
Scriptable b = (Scriptable) obj.get("b", obj);
// Should print "obj.b[0] == x"
System.out.println("obj.b[0] == " + b.get(0, b));
// Should print "obj.b[0] == x"
System.out.println("obj.b[0] == " + b.get(0, b));
// Should print "obj.b[1] == y"
System.out.println("obj.b[1] == " + b.get(1, b));
// Should print "obj.b[1] == y"
System.out.println("obj.b[1] == " + b.get(1, b));
// Should print {a:1, b:["x", "y"]}
Function fn = (Function) ScriptableObject.getProperty(obj, "toString");
System.out.println(fn.call(cx, scope, obj, new Object[0]));
} finally {
Context.exit();
}
// Should print {a:1, b:["x", "y"]}
Function fn = (Function) ScriptableObject.getProperty(obj, "toString");
System.out.println(fn.call(cx, scope, obj, new Object[0]));
} finally {
Context.exit();
}
}
}

Просмотреть файл

@ -169,8 +169,8 @@ public class BaseFunction extends IdScriptableObject implements Function
protected Object getInstanceIdValue(int id)
{
switch (id) {
case Id_length: return wrap_int(getLength());
case Id_arity: return wrap_int(getArity());
case Id_length: return ScriptRuntime.wrapInt(getLength());
case Id_arity: return ScriptRuntime.wrapInt(getArity());
case Id_name: return getFunctionName();
case Id_prototype: return getPrototypeProperty();
case Id_arguments: return getArguments();

Просмотреть файл

@ -725,28 +725,6 @@ public abstract class IdScriptableObject extends ScriptableObject
return f;
}
protected final Object wrap_double(double x)
{
return (x == x) ? new Double(x) : ScriptRuntime.NaNobj;
}
protected final Object wrap_int(int x)
{
return ScriptRuntime.wrapInt(x);
}
protected final Object wrap_long(long x)
{
int i = (int)x;
if (i == x) { return wrap_int(i); }
return new Long(x);
}
protected final Object wrap_boolean(boolean x)
{
return x ? Boolean.TRUE : Boolean.FALSE;
}
private void readObject(ObjectInputStream stream)
throws IOException, ClassNotFoundException
{

Просмотреть файл

@ -128,7 +128,7 @@ public class NativeArray extends IdScriptableObject
protected Object getInstanceIdValue(int id)
{
if (id == Id_length) {
return wrap_double(length);
return ScriptRuntime.wrapNumber(length);
}
return super.getInstanceIdValue(id);
}

Просмотреть файл

@ -66,7 +66,7 @@ final class NativeBoolean extends IdScriptableObject
// This is actually non-ECMA, but will be proposed
// as a change in round 2.
if (typeHint == ScriptRuntime.BooleanClass)
return wrap_boolean(booleanValue);
return ScriptRuntime.wrapBoolean(booleanValue);
return super.getDefaultValue(typeHint);
}
@ -91,37 +91,35 @@ final class NativeBoolean extends IdScriptableObject
return super.execIdCall(f, cx, scope, thisObj, args);
}
int id = f.methodId();
switch (id) {
case Id_constructor: {
if (id == Id_constructor) {
boolean b = ScriptRuntime.toBoolean(args, 0);
if (thisObj == null) {
// new Boolean(val) creates a new boolean object.
return new NativeBoolean(b);
}
// Boolean(val) converts val to a boolean.
return wrap_boolean(b);
}
case Id_toString:
return realThisBoolean(thisObj, f) ? "true" : "false";
case Id_toSource:
if (realThisBoolean(thisObj, f))
return "(new Boolean(true))";
else
return "(new Boolean(false))";
case Id_valueOf:
return wrap_boolean(realThisBoolean(thisObj, f));
return ScriptRuntime.wrapBoolean(b);
}
throw new IllegalArgumentException(String.valueOf(id));
}
private static boolean realThisBoolean(Scriptable thisObj, IdFunctionObject f)
{
// The rest of Boolean.prototype methods require thisObj to be Boolean
if (!(thisObj instanceof NativeBoolean))
throw incompatibleCallError(f);
return ((NativeBoolean)thisObj).booleanValue;
boolean value = ((NativeBoolean)thisObj).booleanValue;
switch (id) {
case Id_toString:
return value ? "true" : "false";
case Id_toSource:
return value ? "(new Boolean(true))" : "(new Boolean(false))";
case Id_valueOf:
return ScriptRuntime.wrapBoolean(value);
}
throw new IllegalArgumentException(String.valueOf(id));
}
// #string_id_map#

Просмотреть файл

@ -57,8 +57,8 @@ final class NativeError extends IdScriptableObject
obj.exportAsJSClass(MAX_PROTOTYPE_ID, scope, sealed);
}
static NativeError make(Context cx, Scriptable scope, IdFunctionObject ctorObj,
Object[] args)
static NativeError make(Context cx, Scriptable scope,
IdFunctionObject ctorObj, Object[] args)
{
Scriptable proto = (Scriptable)(ctorObj.get("prototype", ctorObj));

Просмотреть файл

@ -105,7 +105,7 @@ final class NativeMath extends IdScriptableObject
case Id_SQRT2: x = 1.4142135623730951; name = "SQRT2"; break;
default: throw new IllegalStateException(String.valueOf(id));
}
initPrototypeValue(id, name, wrap_double(x),
initPrototypeValue(id, name, ScriptRuntime.wrapNumber(x),
DONTENUM | READONLY | PERMANENT);
}
}
@ -245,7 +245,7 @@ final class NativeMath extends IdScriptableObject
default: throw new IllegalStateException(String.valueOf(methodId));
}
return wrap_double(x);
return ScriptRuntime.wrapNumber(x);
}
// See Ecma 15.8.2.13

Просмотреть файл

@ -74,11 +74,17 @@ final class NativeNumber extends IdScriptableObject
ctor.defineProperty("NaN", ScriptRuntime.NaNobj, attr);
ctor.defineProperty("POSITIVE_INFINITY",
wrap_double(Double.POSITIVE_INFINITY), attr);
ScriptRuntime.wrapNumber(Double.POSITIVE_INFINITY),
attr);
ctor.defineProperty("NEGATIVE_INFINITY",
wrap_double(Double.NEGATIVE_INFINITY), attr);
ctor.defineProperty("MAX_VALUE", wrap_double(Double.MAX_VALUE), attr);
ctor.defineProperty("MIN_VALUE", wrap_double(Double.MIN_VALUE), attr);
ScriptRuntime.wrapNumber(Double.NEGATIVE_INFINITY),
attr);
ctor.defineProperty("MAX_VALUE",
ScriptRuntime.wrapNumber(Double.MAX_VALUE),
attr);
ctor.defineProperty("MIN_VALUE",
ScriptRuntime.wrapNumber(Double.MIN_VALUE),
attr);
super.fillConstructorProperties(ctor);
}
@ -108,8 +114,7 @@ final class NativeNumber extends IdScriptableObject
return super.execIdCall(f, cx, scope, thisObj, args);
}
int id = f.methodId();
switch (id) {
case Id_constructor: {
if (id == Id_constructor) {
double val = (args.length >= 1)
? ScriptRuntime.toNumber(args[0]) : 0.0;
if (thisObj == null) {
@ -117,59 +122,57 @@ final class NativeNumber extends IdScriptableObject
return new NativeNumber(val);
}
// Number(val) converts val to a number value.
return wrap_double(val);
}
return ScriptRuntime.wrapNumber(val);
}
// The rest of Number.prototype methods require thisObj to be Number
if (!(thisObj instanceof NativeNumber))
throw incompatibleCallError(f);
double value = ((NativeNumber)thisObj).doubleValue;
switch (id) {
case Id_toString:
case Id_toLocaleString: {
// toLocaleString is just an alias for toString for now
double val = realThisValue(thisObj, f);
int base = (args.length == 0)
? 10 : ScriptRuntime.toInt32(args[0]);
return ScriptRuntime.numberToString(val, base);
}
case Id_toLocaleString:
{
// toLocaleString is just an alias for toString for now
int base = (args.length == 0)
? 10 : ScriptRuntime.toInt32(args[0]);
return ScriptRuntime.numberToString(value, base);
}
case Id_toSource: {
double val = realThisValue(thisObj, f);
return "(new Number("+ScriptRuntime.toString(val)+"))";
}
case Id_toSource:
return "(new Number("+ScriptRuntime.toString(value)+"))";
case Id_valueOf:
return wrap_double(realThisValue(thisObj, f));
return ScriptRuntime.wrapNumber(value);
case Id_toFixed:
return num_to(f, thisObj, args, DToA.DTOSTR_FIXED,
return num_to(value, args, DToA.DTOSTR_FIXED,
DToA.DTOSTR_FIXED, -20, 0);
case Id_toExponential:
return num_to(f, thisObj, args, DToA.DTOSTR_STANDARD_EXPONENTIAL,
return num_to(value, args, DToA.DTOSTR_STANDARD_EXPONENTIAL,
DToA.DTOSTR_EXPONENTIAL, 0, 1);
case Id_toPrecision:
return num_to(f, thisObj, args, DToA.DTOSTR_STANDARD,
return num_to(value, args, DToA.DTOSTR_STANDARD,
DToA.DTOSTR_PRECISION, 1, 0);
default: throw new IllegalArgumentException(String.valueOf(id));
}
}
private static double realThisValue(Scriptable thisObj, IdFunctionObject f)
{
if (!(thisObj instanceof NativeNumber))
throw incompatibleCallError(f);
return ((NativeNumber)thisObj).doubleValue;
}
public String toString() {
return ScriptRuntime.numberToString(doubleValue, 10);
}
private static String num_to(IdFunctionObject f, Scriptable thisObj,
private static String num_to(double val,
Object[] args,
int zeroArgMode, int oneArgMode,
int precisionMin, int precisionOffset)
{
double val = realThisValue(thisObj, f);
int precision;
if (args.length == 0) {
precision = 0;

Просмотреть файл

@ -93,7 +93,7 @@ final class NativeString extends IdScriptableObject
protected Object getInstanceIdValue(int id)
{
if (id == Id_length) {
return wrap_int(string.length());
return ScriptRuntime.wrapInt(string.length());
}
return super.getInstanceIdValue(id);
}
@ -199,15 +199,15 @@ final class NativeString extends IdScriptableObject
}
char c = target.charAt((int)pos);
if (id == Id_charAt) return String.valueOf(c);
else return wrap_int(c);
else return ScriptRuntime.wrapInt(c);
}
case Id_indexOf:
return wrap_int(js_indexOf(
return ScriptRuntime.wrapInt(js_indexOf(
ScriptRuntime.toString(thisObj), args));
case Id_lastIndexOf:
return wrap_int(js_lastIndexOf(
return ScriptRuntime.wrapInt(js_lastIndexOf(
ScriptRuntime.toString(thisObj), args));
case Id_split:
@ -276,8 +276,8 @@ final class NativeString extends IdScriptableObject
case Id_equalsIgnoreCase: {
String s1 = ScriptRuntime.toString(thisObj);
String s2 = ScriptRuntime.toString(args, 0);
return wrap_boolean(id == Id_equals
? s1.equals(s2) : s1.equalsIgnoreCase(s2));
return ScriptRuntime.wrapBoolean(
(id == Id_equals) ? s1.equals(s2) : s1.equalsIgnoreCase(s2));
}
case Id_match:

Просмотреть файл

@ -215,6 +215,24 @@ public class ScriptRuntime {
return new Integer(i);
}
public static Number wrapNumber(double x)
{
int i = (int)x;
if ((double)i == x) {
if (i == 0) {
if (1.0 / x < 0) {
// x is -0.0
return new Double(x);
}
}
return wrapInt(i);
}
if (x != x) {
return ScriptRuntime.NaNobj;
}
return new Double(x);
}
/**
* Convert the value to a boolean.
*

Просмотреть файл

@ -2647,16 +2647,16 @@ System.out.println("Testing at " + x.cp + ", op = " + op);
protected Object getInstanceIdValue(int id)
{
switch (id) {
case Id_lastIndex:
return wrap_double(lastIndex);
case Id_source:
return new String(re.source);
case Id_global:
return wrap_boolean((re.flags & JSREG_GLOB) != 0);
case Id_ignoreCase:
return wrap_boolean((re.flags & JSREG_FOLD) != 0);
case Id_multiline:
return wrap_boolean((re.flags & JSREG_MULTILINE) != 0);
case Id_lastIndex:
return ScriptRuntime.wrapNumber(lastIndex);
case Id_source:
return new String(re.source);
case Id_global:
return ScriptRuntime.wrapBoolean((re.flags & JSREG_GLOB) != 0);
case Id_ignoreCase:
return ScriptRuntime.wrapBoolean((re.flags & JSREG_FOLD) != 0);
case Id_multiline:
return ScriptRuntime.wrapBoolean((re.flags & JSREG_MULTILINE) != 0);
}
return super.getInstanceIdValue(id);
}

Просмотреть файл

@ -229,7 +229,7 @@ public class NativeRegExpCtor extends NativeFunction {
switch (shifted) {
case Id_multiline:
case Id_STAR:
return wrap_boolean(impl.multiline);
return ScriptRuntime.wrapBoolean(impl.multiline);
case Id_input:
case Id_UNDERSCORE:

Просмотреть файл

@ -179,7 +179,7 @@ public class Global extends ImporterTopLevel {
public static void defineClass(Context cx, Scriptable thisObj,
Object[] args, Function funObj)
throws IllegalAccessException, InstantiationException,
InvocationTargetException, ClassDefinitionException
InvocationTargetException
{
Class clazz = getClass(args);
ScriptableObject.defineClass(thisObj, clazz);

Просмотреть файл

@ -493,16 +493,22 @@ abstract class XMLObjectImpl extends XMLObject
return super.execIdCall(f, cx, scope, thisObj, args);
}
int id = f.methodId();
switch (id) {
case Id_constructor: {
if (id == Id_constructor) {
return jsConstructor(cx, thisObj == null, args);
}
}
// All (XML|XMLList).prototype methods require thisObj to be XML
if (!(thisObj instanceof XMLObjectImpl))
throw incompatibleCallError(f);
XMLObjectImpl realThis = (XMLObjectImpl)thisObj;
switch (id) {
case Id_addNamespace: {
Namespace ns = lib.castToNamespace(cx, arg(args, 0));
return realThis(thisObj, f).addNamespace(ns);
return realThis.addNamespace(ns);
}
case Id_appendChild:
return realThis(thisObj, f).appendChild(arg(args, 0));
return realThis.appendChild(arg(args, 0));
case Id_attribute: {
Object arg0 = arg(args, 0);
if (arg0 == null || arg0 == Undefined.instance) {
@ -512,103 +518,104 @@ abstract class XMLObjectImpl extends XMLObject
arg0 = ScriptRuntime.toString(arg0);
}
XMLName xmlName = lib.toAttributeNameImpl(cx, arg0);
return realThis(thisObj, f).attribute(xmlName);
return realThis.attribute(xmlName);
}
case Id_attributes:
return realThis(thisObj, f).attributes();
return realThis.attributes();
case Id_child: {
XMLName xmlName = getXmlNameOrIndex(cx, args, 0);
XMLName xmlName = lib.toXMLNameOrIndex(cx, arg(args, 0));
if (xmlName == null) {
long index = ScriptRuntime.lastUint32Result(cx);
return realThis(thisObj, f).child(index);
return realThis.child(index);
} else {
return realThis(thisObj, f).child(xmlName);
return realThis.child(xmlName);
}
}
case Id_childIndex:
return new Integer(realThis(thisObj, f).childIndex());
return ScriptRuntime.wrapInt(realThis.childIndex());
case Id_children:
return realThis(thisObj, f).children();
return realThis.children();
case Id_comments:
return realThis(thisObj, f).comments();
return realThis.comments();
case Id_contains:
return wrap_boolean(realThis(thisObj, f).contains(arg(args, 0)));
return ScriptRuntime.wrapBoolean(
realThis.contains(arg(args, 0)));
case Id_copy:
return realThis(thisObj, f).copy();
return realThis.copy();
case Id_descendants: {
XMLName xmlName = (args.length == 0)
? XMLName.formStar()
: lib.toXMLName(cx, args[0]);
return realThis(thisObj, f).descendants(xmlName);
return realThis.descendants(xmlName);
}
case Id_inScopeNamespaces: {
Object[] array = realThis(thisObj, f).inScopeNamespaces();
Object[] array = realThis.inScopeNamespaces();
return cx.newArray(scope, array);
}
case Id_insertChildAfter:
return realThis(thisObj, f).insertChildAfter(arg(args, 0), arg(args, 1));
return realThis.insertChildAfter(arg(args, 0), arg(args, 1));
case Id_insertChildBefore:
return realThis(thisObj, f).insertChildBefore(arg(args, 0), arg(args, 1));
return realThis.insertChildBefore(arg(args, 0), arg(args, 1));
case Id_hasOwnProperty: {
XMLName xmlName = lib.toXMLName(cx, arg(args, 0));
return wrap_boolean(
realThis(thisObj, f).hasOwnProperty(xmlName));
return ScriptRuntime.wrapBoolean(
realThis.hasOwnProperty(xmlName));
}
case Id_hasComplexContent:
return wrap_boolean(realThis(thisObj, f).hasComplexContent());
return ScriptRuntime.wrapBoolean(realThis.hasComplexContent());
case Id_hasSimpleContent:
return wrap_boolean(realThis(thisObj, f).hasSimpleContent());
return ScriptRuntime.wrapBoolean(realThis.hasSimpleContent());
case Id_length:
return new Integer(realThis(thisObj, f).length());
return ScriptRuntime.wrapInt(realThis.length());
case Id_localName:
return realThis(thisObj, f).localName();
return realThis.localName();
case Id_name:
return realThis(thisObj, f).name();
return realThis.name();
case Id_namespace: {
String prefix = (args.length > 0)
? ScriptRuntime.toString(args[0]) : null;
return realThis(thisObj, f).namespace(prefix);
return realThis.namespace(prefix);
}
case Id_namespaceDeclarations: {
Object[] array = realThis(thisObj, f).namespaceDeclarations();
Object[] array = realThis.namespaceDeclarations();
return cx.newArray(scope, array);
}
case Id_nodeKind:
return realThis(thisObj, f).nodeKind();
return realThis.nodeKind();
case Id_normalize:
realThis(thisObj, f).normalize();
realThis.normalize();
return Undefined.instance;
case Id_parent:
return realThis(thisObj, f).parent();
return realThis.parent();
case Id_prependChild:
return realThis(thisObj, f).prependChild(arg(args, 0));
return realThis.prependChild(arg(args, 0));
case Id_processingInstructions: {
XMLName xmlName = (args.length > 0)
? lib.toXMLName(cx, args[0])
: XMLName.formStar();
return realThis(thisObj, f).processingInstructions(xmlName);
return realThis.processingInstructions(xmlName);
}
case Id_propertyIsEnumerable: {
XMLName xmlName = lib.toXMLName(cx, arg(args, 0));
return wrap_boolean(
realThis(thisObj, f).propertyIsEnumerable(xmlName));
return ScriptRuntime.wrapBoolean(
realThis.propertyIsEnumerable(xmlName));
}
case Id_removeNamespace: {
Namespace ns = lib.castToNamespace(cx, arg(args, 0));
return realThis(thisObj, f).removeNamespace(ns);
return realThis.removeNamespace(ns);
}
case Id_replace: {
XMLName xmlName = getXmlNameOrIndex(cx, args, 0);
XMLName xmlName = lib.toXMLNameOrIndex(cx, arg(args, 0));
Object arg1 = arg(args, 1);
if (xmlName == null) {
long index = ScriptRuntime.lastUint32Result(cx);
return realThis(thisObj, f).replace(index, arg1);
return realThis.replace(index, arg1);
} else {
return realThis(thisObj, f).replace(xmlName, arg1);
return realThis.replace(xmlName, arg1);
}
}
case Id_setChildren:
return realThis(thisObj, f).setChildren(arg(args, 0));
return realThis.setChildren(arg(args, 0));
case Id_setLocalName: {
String localName;
Object arg = arg(args, 0);
@ -617,7 +624,7 @@ abstract class XMLObjectImpl extends XMLObject
} else {
localName = ScriptRuntime.toString(arg);
}
realThis(thisObj, f).setLocalName(localName);
realThis.setLocalName(localName);
return Undefined.instance;
}
case Id_setName: {
@ -634,53 +641,35 @@ abstract class XMLObjectImpl extends XMLObject
} else {
qname = lib.constructQName(cx, arg);
}
realThis(thisObj, f).setName(qname);
realThis.setName(qname);
return Undefined.instance;
}
case Id_setNamespace: {
Namespace ns = lib.castToNamespace(cx, arg(args, 0));
realThis(thisObj, f).setNamespace(ns);
realThis.setNamespace(ns);
return Undefined.instance;
}
case Id_text:
return realThis(thisObj, f).text();
return realThis.text();
case Id_toString:
return realThis(thisObj, f).toString();
return realThis.toString();
case Id_toSource: {
int indent = ScriptRuntime.toInt32(args, 0);
return realThis(thisObj, f).toSource(indent);
return realThis.toSource(indent);
}
case Id_toXMLString: {
int indent = ScriptRuntime.toInt32(args, 0);
return realThis(thisObj, f).toXMLString(indent);
return realThis.toXMLString(indent);
}
case Id_valueOf:
return realThis(thisObj, f).valueOf();
return realThis.valueOf();
}
throw new IllegalArgumentException(String.valueOf(id));
}
/**
*
* @param thisObj
* @param f
* @return
*/
private XMLObjectImpl realThis(Scriptable thisObj, IdFunctionObject f)
{
if(!(thisObj instanceof XMLObjectImpl))
throw incompatibleCallError(f);
return (XMLObjectImpl)thisObj;
}
private static Object arg(Object[] args, int i)
{
return (i < args.length) ? args[i] : Undefined.instance;
}
private XMLName getXmlNameOrIndex(Context cx, Object[] args, int i)
{
return lib.toXMLNameOrIndex(cx, arg(args, i));
}
}