Try proxying all function arguments
authorjfbastien@apple.com <jfbastien@apple.com@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Sat, 2 Dec 2017 06:48:27 +0000 (06:48 +0000)
committerjfbastien@apple.com <jfbastien@apple.com@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Sat, 2 Dec 2017 06:48:27 +0000 (06:48 +0000)
https://bugs.webkit.org/show_bug.cgi?id=180306

Reviewed by Saam Barati.

* stress/proxy-all-the-parameters.js: Added.
(isPropertyOfType):
(getProperties):
(generateObjects):
(getObjects):
(getFunctions):
(get throw):
(let.o.of.getObjects.let.f.of.getFunctions.catch):

git-svn-id: https://svn.webkit.org/repository/webkit/trunk@225444 268f45cc-cd09-0410-ab3c-d52691b4dbfc

JSTests/ChangeLog
JSTests/stress/proxy-all-the-parameters.js [new file with mode: 0644]

index 53948b1..94477a5 100644 (file)
@@ -1,5 +1,21 @@
 2017-12-01  JF Bastien  <jfbastien@apple.com>
 
+        Try proxying all function arguments
+        https://bugs.webkit.org/show_bug.cgi?id=180306
+
+        Reviewed by Saam Barati.
+
+        * stress/proxy-all-the-parameters.js: Added.
+        (isPropertyOfType):
+        (getProperties):
+        (generateObjects):
+        (getObjects):
+        (getFunctions):
+        (get throw):
+        (let.o.of.getObjects.let.f.of.getFunctions.catch):
+
+2017-12-01  JF Bastien  <jfbastien@apple.com>
+
         JavaScriptCore: missing exception checks in Math functions that take more than one argument
         https://bugs.webkit.org/show_bug.cgi?id=180297
         <rdar://problem/35745556>
diff --git a/JSTests/stress/proxy-all-the-parameters.js b/JSTests/stress/proxy-all-the-parameters.js
new file mode 100644 (file)
index 0000000..ba1a4ce
--- /dev/null
@@ -0,0 +1,70 @@
+const verbose = false;
+
+const ignore = ['quit', 'readline', 'waitForReport', 'flashHeapAccess', 'leaving', 'getReport'];
+
+function isPropertyOfType(obj, name, type) {
+    let desc;
+    desc = Object.getOwnPropertyDescriptor(obj, name)
+    return typeof type === 'undefined' || typeof desc.value === type;
+}
+
+function getProperties(obj, type) {
+    let properties = [];
+    for (let name of Object.getOwnPropertyNames(obj)) {
+        if (isPropertyOfType(obj, name, type))
+            properties.push(name);
+    }
+    return properties;
+}
+
+function* generateObjects(root = this, level = 0) {
+    if (level > 4)
+        return;
+    let obj_names = getProperties(root, 'object');
+    for (let obj_name of obj_names) {
+        let obj = root[obj_name];
+        yield obj;
+        yield* generateObjects(obj, level + 1);
+    }
+}
+
+function getObjects() {
+    let objects = [];
+    for (let obj of generateObjects())
+        if (!objects.includes(obj))
+            objects.push(obj);
+    return objects;
+}
+
+function getFunctions(obj) {
+    return getProperties(obj, 'function');
+}
+
+const thrower = new Proxy({}, { get() { throw 0xc0defefe; } });
+
+for (let o of getObjects()) {
+    for (let f of getFunctions(o)) {
+        if (ignore.includes(f))
+            continue;
+        const arityPlusOne = o[f].length + 1;
+        if (verbose)
+            print(`Calling ${o}['${f}'](${Array(arityPlusOne).fill("thrower")})`);
+        try {
+            o[f](Array(arityPlusOne).fill(thrower));
+        } catch (e) {
+            if (`${e}`.includes('constructor without new is invalid')) {
+                try {
+                    if (verbose)
+                        print(`    Constructing instead`);
+                    new o[f](Array(arityPlusOne).fill(thrower));
+                } catch (e) {
+                    if (verbose)
+                        print(`    threw ${e}`);
+                }
+            } else {
+                if (verbose)
+                    print(`    threw ${e}`);
+            }
+        }
+    }
+}