Revision: 22452
Author: [email protected]
Date: Thu Jul 17 15:07:59 2014 UTC
Log: Expose the content of Maps and WeakMaps through MapMirror.
BUG=v8:3291
LOG=N
[email protected], [email protected]
Review URL: https://codereview.chromium.org/398513005
Patch from Alexandra Mikhaylova <[email protected]>.
http://code.google.com/p/v8/source/detail?r=22452
Added:
/branches/bleeding_edge/test/mjsunit/harmony/mirror-collections.js
/branches/bleeding_edge/test/mjsunit/runtime-gen/getweakmapentries.js
Modified:
/branches/bleeding_edge/src/mirror-debugger.js
/branches/bleeding_edge/src/runtime.cc
/branches/bleeding_edge/src/runtime.h
/branches/bleeding_edge/tools/generate-runtime-tests.py
=======================================
--- /dev/null
+++ /branches/bleeding_edge/test/mjsunit/harmony/mirror-collections.js Thu
Jul 17 15:07:59 2014 UTC
@@ -0,0 +1,95 @@
+// Copyright 2014 the V8 project authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+// Flags: --expose-debug-as debug --expose-gc --harmony-collections
+
+function testMapMirror(mirror) {
+ // Create JSON representation.
+ var serializer = debug.MakeMirrorSerializer();
+ var json = JSON.stringify(serializer.serializeValue(mirror));
+
+ // Check the mirror hierachy.
+ assertTrue(mirror instanceof debug.Mirror);
+ assertTrue(mirror instanceof debug.ValueMirror);
+ assertTrue(mirror instanceof debug.ObjectMirror);
+ assertTrue(mirror instanceof debug.MapMirror);
+
+ assertTrue(mirror.isMap());
+
+ // Parse JSON representation and check.
+ var fromJSON = eval('(' + json + ')');
+ assertEquals('map', fromJSON.type);
+}
+
+var o1 = new Object();
+var o2 = new Object();
+var o3 = new Object();
+
+// Test the mirror object for Maps
+var map = new Map();
+map.set(o1, 11);
+map.set(o2, 22);
+map.delete(o1);
+var mapMirror = debug.MakeMirror(map);
+testMapMirror(mapMirror);
+var entries = mapMirror.entries();
+assertEquals(1, entries.length);
+assertSame(o2, entries[0].key);
+assertEquals(22, entries[0].value);
+map.set(o1, 33);
+map.set(o3, o2);
+map.delete(o2);
+map.set(undefined, 44);
+entries = mapMirror.entries();
+assertEquals(3, entries.length);
+assertSame(o1, entries[0].key);
+assertEquals(33, entries[0].value);
+assertSame(o3, entries[1].key);
+assertSame(o2, entries[1].value);
+assertEquals(undefined, entries[2].key);
+assertEquals(44, entries[2].value);
+
+// Test the mirror object for WeakMaps
+var weakMap = new WeakMap();
+weakMap.set(o1, 11);
+weakMap.set(new Object(), 22);
+weakMap.set(o3, 33);
+var weakMapMirror = debug.MakeMirror(weakMap);
+testMapMirror(weakMapMirror);
+
+function testWeakMapEntries(entries, gcDone) {
+ var found = 0;
+ for (var i = 0; i < entries.length; i++) {
+ if (Object.is(entries[i].key, o1)) {
+ assertEquals(11, entries[i].value);
+ found++;
+ continue;
+ }
+ if (Object.is(entries[i].key, o3)) {
+ assertEquals(33, entries[i].value);
+ found++;
+ continue;
+ }
+ if (!gcDone && entries[i].value == 22)
+ found++;
+ }
+ return found;
+}
+
+function testWeakMapMirrorBeforeGC(mirror) {
+ var entries = mirror.entries();
+ assertEquals(3, entries.length);
+ assertEquals(3, testWeakMapEntries(entries, false));
+}
+
+testWeakMapMirrorBeforeGC(weakMapMirror);
+gc();
+
+function testWeakMapMirrorAfterGC(mirror) {
+ var entries = mirror.entries();
+ assertEquals(2, entries.length);
+ assertEquals(2, testWeakMapEntries(entries, true));
+}
+
+testWeakMapMirrorAfterGC(weakMapMirror);
=======================================
--- /dev/null
+++ /branches/bleeding_edge/test/mjsunit/runtime-gen/getweakmapentries.js
Thu Jul 17 15:07:59 2014 UTC
@@ -0,0 +1,5 @@
+// Copyright 2014 the V8 project authors. All rights reserved.
+// AUTO-GENERATED BY tools/generate-runtime-tests.py, DO NOT MODIFY
+// Flags: --allow-natives-syntax --harmony
+var _holder = new WeakMap();
+%GetWeakMapEntries(_holder);
=======================================
--- /branches/bleeding_edge/src/mirror-debugger.js Tue Jun 10 09:42:41 2014
UTC
+++ /branches/bleeding_edge/src/mirror-debugger.js Thu Jul 17 15:07:59 2014
UTC
@@ -81,6 +81,8 @@
mirror = new ErrorMirror(value);
} else if (IS_SCRIPT(value)) {
mirror = new ScriptMirror(value);
+ } else if (IS_MAP(value) || IS_WEAKMAP(value)) {
+ mirror = new MapMirror(value);
} else if (ObjectIsPromise(value)) {
mirror = new PromiseMirror(value);
} else {
@@ -155,6 +157,7 @@
var CONTEXT_TYPE = 'context';
var SCOPE_TYPE = 'scope';
var PROMISE_TYPE = 'promise';
+var MAP_TYPE = 'map';
// Maximum length when sending strings through the JSON protocol.
var kMaxProtocolStringLength = 80;
@@ -210,6 +213,7 @@
// - RegExpMirror
// - ErrorMirror
// - PromiseMirror
+// - MapMirror
// - PropertyMirror
// - InternalPropertyMirror
// - FrameMirror
@@ -420,6 +424,15 @@
};
+/**
+ * Check whether the mirror reflects a map.
+ * @returns {boolean} True if the mirror reflects a map
+ */
+Mirror.prototype.isMap = function() {
+ return this instanceof MapMirror;
+};
+
+
/**
* Allocate a handle id for this object.
*/
@@ -1253,6 +1266,44 @@
};
+function MapMirror(value) {
+ %_CallFunction(this, value, MAP_TYPE, ObjectMirror);
+}
+inherits(MapMirror, ObjectMirror);
+
+
+/**
+ * Returns an array of key/value pairs of a map.
+ * This will keep keys alive for WeakMaps.
+ *
+ * @returns {Array.<Object>} Array of key/value pairs of a map.
+ */
+MapMirror.prototype.entries = function() {
+ var result = [];
+
+ if (IS_WEAKMAP(this.value_)) {
+ var entries = %GetWeakMapEntries(this.value_);
+ for (var i = 0; i < entries.length; i += 2) {
+ result.push({
+ key: entries[i],
+ value: entries[i + 1]
+ });
+ }
+ return result;
+ }
+
+ var iter = %_CallFunction(this.value_, builtins.MapEntries);
+ var next;
+ while (!(next = iter.next()).done) {
+ result.push({
+ key: next.value[0],
+ value: next.value[1]
+ });
+ }
+ return result;
+};
+
+
/**
* Base mirror object for properties.
* @param {ObjectMirror} mirror The mirror object having this property
=======================================
--- /branches/bleeding_edge/src/runtime.cc Thu Jul 17 09:44:37 2014 UTC
+++ /branches/bleeding_edge/src/runtime.cc Thu Jul 17 15:07:59 2014 UTC
@@ -1704,6 +1704,29 @@
holder->set_kind(Smi::FromInt(kind));
return isolate->heap()->undefined_value();
}
+
+
+RUNTIME_FUNCTION(Runtime_GetWeakMapEntries) {
+ HandleScope scope(isolate);
+ ASSERT(args.length() == 1);
+ CONVERT_ARG_HANDLE_CHECKED(JSWeakCollection, holder, 0);
+ Handle<ObjectHashTable> table(ObjectHashTable::cast(holder->table()));
+ Handle<FixedArray> entries =
+ isolate->factory()->NewFixedArray(table->NumberOfElements() * 2);
+ {
+ DisallowHeapAllocation no_gc;
+ int number_of_non_hole_elements = 0;
+ for (int i = 0; i < table->Capacity(); i++) {
+ Handle<Object> key(table->KeyAt(i), isolate);
+ if (table->IsKey(*key)) {
+ entries->set(number_of_non_hole_elements++, *key);
+ entries->set(number_of_non_hole_elements++, table->Lookup(key));
+ }
+ }
+ ASSERT_EQ(table->NumberOfElements() * 2, number_of_non_hole_elements);
+ }
+ return *isolate->factory()->NewJSArrayWithElements(entries);
+}
RUNTIME_FUNCTION(Runtime_MapIteratorNext) {
=======================================
--- /branches/bleeding_edge/src/runtime.h Wed Jul 16 12:03:33 2014 UTC
+++ /branches/bleeding_edge/src/runtime.h Thu Jul 17 15:07:59 2014 UTC
@@ -296,6 +296,8 @@
F(WeakCollectionDelete, 2, 1) \
F(WeakCollectionSet, 3, 1) \
\
+ F(GetWeakMapEntries, 1, 1) \
+ \
/* Harmony events */ \
F(EnqueueMicrotask, 1, 1) \
F(RunMicrotasks, 0, 1) \
=======================================
--- /branches/bleeding_edge/tools/generate-runtime-tests.py Wed Jul 16
14:00:15 2014 UTC
+++ /branches/bleeding_edge/tools/generate-runtime-tests.py Thu Jul 17
15:07:59 2014 UTC
@@ -47,11 +47,11 @@
# that the parser doesn't bit-rot. Change the values as needed when you
add,
# remove or change runtime functions, but make sure we don't lose our
ability
# to parse them!
-EXPECTED_FUNCTION_COUNT = 417
-EXPECTED_FUZZABLE_COUNT = 332
+EXPECTED_FUNCTION_COUNT = 418
+EXPECTED_FUZZABLE_COUNT = 333
EXPECTED_CCTEST_COUNT = 8
EXPECTED_UNKNOWN_COUNT = 4
-EXPECTED_BUILTINS_COUNT = 809
+EXPECTED_BUILTINS_COUNT = 810
# Don't call these at all.
--
--
v8-dev mailing list
[email protected]
http://groups.google.com/group/v8-dev
---
You received this message because you are subscribed to the Google Groups "v8-dev" group.
To unsubscribe from this group and stop receiving emails from it, send an email
to [email protected].
For more options, visit https://groups.google.com/d/optout.