From eea8cc1e97d4278f5fa255d28eff3d355e0df97b Mon Sep 17 00:00:00 2001 From: "nboyd%atg.com" Date: Sat, 8 Aug 2009 20:56:57 +0000 Subject: [PATCH] Made getOwnPropertDescriptor use the actual attributes for builtins, rather than the isMethod heuristic. Patch from Raphael Speyer. git-svn-id: svn://10.0.0.236/trunk@258016 18797224-902f-48f8-a5cc-f745e15eee43 --- .../javascript/IdScriptableObject.java | 41 +++++++++++++------ .../mozilla/javascript/ScriptableObject.java | 22 ++++++---- .../doctests/object.defineproperty.doctest | 2 +- 3 files changed, 44 insertions(+), 21 deletions(-) diff --git a/mozilla/js/rhino/src/org/mozilla/javascript/IdScriptableObject.java b/mozilla/js/rhino/src/org/mozilla/javascript/IdScriptableObject.java index 133153ca6e9..87be0a694a4 100644 --- a/mozilla/js/rhino/src/org/mozilla/javascript/IdScriptableObject.java +++ b/mozilla/js/rhino/src/org/mozilla/javascript/IdScriptableObject.java @@ -720,23 +720,38 @@ public abstract class IdScriptableObject extends ScriptableObject protected ScriptableObject getOwnPropertyDescriptor(Context cx, Object id) { ScriptableObject desc = super.getOwnPropertyDescriptor(cx, id); if (desc == null && id instanceof String) { - Object value = get((String) id, this); - if (value != NOT_FOUND) { - boolean isMethod = (value instanceof Callable); - - desc = new NativeObject(); - Scriptable scope = getParentScope(); - ScriptRuntime.setObjectProtoAndParent(desc, (scope == null ? this : scope)); - - desc.defineProperty("value", value, EMPTY); - desc.defineProperty("enumerable", false, EMPTY); - desc.defineProperty("writable", isMethod, EMPTY); - desc.defineProperty("configurable", isMethod, EMPTY); - } + desc = getBuiltInDescriptor((String) id); } return desc; } + private ScriptableObject getBuiltInDescriptor(String name) { + Object value = null; + int attr = EMPTY; + + Scriptable scope = getParentScope(); + if (scope == null) { + scope = this; + } + + int info = findInstanceIdInfo(name); + if (info != 0) { + int id = (info & 0xFFFF); + value = getInstanceIdValue(id); + attr = (info >>> 16); + return buildDataDescriptor(scope, value, attr); + } + if (prototypeValues != null) { + int id = prototypeValues.findId(name); + if (id != 0) { + value = prototypeValues.get(id); + attr = prototypeValues.getAttributes(id); + return buildDataDescriptor(scope, value, attr); + } + } + return null; + } + private void readObject(ObjectInputStream stream) throws IOException, ClassNotFoundException { diff --git a/mozilla/js/rhino/src/org/mozilla/javascript/ScriptableObject.java b/mozilla/js/rhino/src/org/mozilla/javascript/ScriptableObject.java index 395685512df..c7c8fb75d4d 100644 --- a/mozilla/js/rhino/src/org/mozilla/javascript/ScriptableObject.java +++ b/mozilla/js/rhino/src/org/mozilla/javascript/ScriptableObject.java @@ -206,17 +206,25 @@ public abstract class ScriptableObject implements Scriptable, Serializable, } ScriptableObject getPropertyDescriptor(Context cx, Scriptable scope) { - ScriptableObject desc = new NativeObject(); - ScriptRuntime.setObjectProtoAndParent(desc, scope); - if (value != null) desc.defineProperty("value", value, EMPTY); - desc.defineProperty("writable", (attributes & READONLY) == 0, EMPTY); - desc.defineProperty("enumerable", (attributes & DONTENUM) == 0, EMPTY); - desc.defineProperty("configurable", (attributes & PERMANENT) == 0, EMPTY); - return desc; + return buildDataDescriptor( + scope, + (value == null ? Undefined.instance : value), + attributes); } } + protected static ScriptableObject buildDataDescriptor(Scriptable scope, Object value, int attributes) { + ScriptableObject desc = new NativeObject(); + ScriptRuntime.setObjectProtoAndParent(desc, scope); + + desc.defineProperty("value", value, EMPTY); + desc.defineProperty("writable", (attributes & READONLY) == 0, EMPTY); + desc.defineProperty("enumerable", (attributes & DONTENUM) == 0, EMPTY); + desc.defineProperty("configurable", (attributes & PERMANENT) == 0, EMPTY); + return desc; + } + private static final class GetterSlot extends Slot { static final long serialVersionUID = -4900574849788797588L; diff --git a/mozilla/js/rhino/testsrc/doctests/object.defineproperty.doctest b/mozilla/js/rhino/testsrc/doctests/object.defineproperty.doctest index 713b2e5bd60..52b9e6a4f19 100644 --- a/mozilla/js/rhino/testsrc/doctests/object.defineproperty.doctest +++ b/mozilla/js/rhino/testsrc/doctests/object.defineproperty.doctest @@ -32,7 +32,7 @@ js> var describe = Object.getOwnPropertyDescriptor; js> // when define new property with empty descriptor then default values are used for the descriptor js> var obj = define({}, 'a', {}); js> describe(obj, 'a').toSource() -({writable:false, enumerable:false, configurable:false}) +({value:undefined, writable:false, enumerable:false, configurable:false}) js> // when define new property with data descriptor then those values are used for the descriptor js> var obj = define({}, 'a', { value: 2, writable: true });