Index: src/v8natives.js |
diff --git a/src/v8natives.js b/src/v8natives.js |
index 0afe231c8cdbf2863cc281a7110a9025f581683f..738e08f0baabf9796b39269dc50f778b5f63d429 100644 |
--- a/src/v8natives.js |
+++ b/src/v8natives.js |
@@ -354,6 +354,19 @@ function FromPropertyDescriptor(desc) { |
return obj; |
} |
+// Harmony Proxies |
+function FromGenericPropertyDescriptor(desc) { |
+ if (IS_UNDEFINED(desc)) return desc; |
+ var obj = new $Object(); |
+ if (desc.hasValue_) obj.value = desc.getValue(); |
Kevin Millikin (Chromium)
2011/07/07 08:12:02
It's not obvious why you use the property hasValue
rossberg
2011/07/07 09:19:32
True. I copied from pre-existing functions. I fixe
|
+ if (desc.hasWritable_) obj.writable = desc.isWritable(); |
+ if (desc.hasGetter_) obj.get = desc.getGet(); |
+ if (desc.hasSetter_) obj.set = desc.getSet(); |
+ if (desc.hasEnumerable_) obj.enumerable = desc.isEnumerable(); |
+ if (desc.hasConfigurable_) obj.configurable = desc.isConfigurable(); |
+ return obj; |
+} |
+ |
// ES5 8.10.5. |
function ToPropertyDescriptor(obj) { |
if (!IS_SPEC_OBJECT(obj)) { |
@@ -616,8 +629,32 @@ function GetOwnProperty(obj, p) { |
} |
+// Harmony proxies. |
+function DefineProxyProperty(obj, p, attributes, should_throw) { |
+ var handler = %GetHandler(obj); |
+ var defineProperty = handler.defineProperty; |
+ if (IS_UNDEFINED(defineProperty)) { |
+ throw MakeTypeError("handler_trap_missing", [handler, "defineProperty"]); |
+ } |
+ var result = defineProperty.call(handler, p, attributes); |
+ if (!ToBoolean(result)) { |
+ if (should_throw) { |
+ throw MakeTypeError("handler_failed", [handler, "defineProperty"]); |
+ } else { |
+ return false; |
+ } |
+ } |
+ return true; |
+} |
+ |
+ |
// ES5 8.12.9. |
function DefineOwnProperty(obj, p, desc, should_throw) { |
+ if (%IsJSProxy(obj)) { |
+ var attributes = FromGenericPropertyDescriptor(desc); |
+ return DefineProxyProperty(obj, p, attributes, should_throw); |
+ } |
+ |
var current_or_access = %GetOwnProperty(ToObject(obj), ToString(p)); |
// A false value here means that access checks failed. |
if (current_or_access === false) return void 0; |
@@ -900,8 +937,37 @@ function ObjectDefineProperty(obj, p, attributes) { |
throw MakeTypeError("obj_ctor_property_non_object", ["defineProperty"]); |
} |
var name = ToString(p); |
- var desc = ToPropertyDescriptor(attributes); |
- DefineOwnProperty(obj, name, desc, true); |
+ if (%IsJSProxy(obj)) { |
+ // Clone the attributes object for protection. |
+ // TODO(rossberg): not spec'ed yet, so not sure if this should involve |
+ // non-own properties as it does (or non-enumerable ones, as it doesn't?). |
+ var attributesClone = {} |
+ for (var a in attributes) { |
+ attributesClone[a] = attributes[a]; |
+ } |
+ DefineProxyProperty(obj, name, attributesClone, true); |
+ // The following would implement the spec as in the current proposal, |
+ // but after recent comments on es-discuss, is most likely obsolete. |
+ /* |
+ var defineObj = FromGenericPropertyDescriptor(desc); |
+ var names = ObjectGetOwnPropertyNames(attributes); |
+ var standardNames = |
+ {value: 0, writable: 0, get: 0, set: 0, enumerable: 0, configurable: 0}; |
+ for (var i = 0; i < names.length; i++) { |
+ var N = names[i]; |
+ if (!(%HasLocalProperty(standardNames, N))) { |
+ var attr = GetOwnProperty(attributes, N); |
+ DefineOwnProperty(descObj, N, attr, true); |
+ } |
+ } |
+ // This is really confusing the types, but it is what the proxies spec |
+ // currently requires: |
+ desc = descObj; |
+ */ |
+ } else { |
+ var desc = ToPropertyDescriptor(attributes); |
+ DefineOwnProperty(obj, name, desc, true); |
+ } |
return obj; |
} |