summaryrefslogtreecommitdiffstats
path: root/js/src/tests/ecma_5/RegExp
diff options
context:
space:
mode:
Diffstat (limited to 'js/src/tests/ecma_5/RegExp')
-rw-r--r--js/src/tests/ecma_5/RegExp/15.10.5-01.js21
-rw-r--r--js/src/tests/ecma_5/RegExp/15.10.7.5-01.js71
-rw-r--r--js/src/tests/ecma_5/RegExp/7.8.5-01.js35
-rw-r--r--js/src/tests/ecma_5/RegExp/browser.js0
-rw-r--r--js/src/tests/ecma_5/RegExp/empty-lookahead.js8
-rw-r--r--js/src/tests/ecma_5/RegExp/exec-lastIndex-ToInteger.js36
-rw-r--r--js/src/tests/ecma_5/RegExp/exec.js240
-rw-r--r--js/src/tests/ecma_5/RegExp/instance-property-storage-introspection.js131
-rw-r--r--js/src/tests/ecma_5/RegExp/regexp-space-character-class.js45
-rw-r--r--js/src/tests/ecma_5/RegExp/regress-429241.js200
-rw-r--r--js/src/tests/ecma_5/RegExp/regress-576828.js8
-rw-r--r--js/src/tests/ecma_5/RegExp/regress-613820-1.js9
-rw-r--r--js/src/tests/ecma_5/RegExp/regress-613820-2.js9
-rw-r--r--js/src/tests/ecma_5/RegExp/regress-613820-3.js9
-rw-r--r--js/src/tests/ecma_5/RegExp/regress-617935.js42
-rw-r--r--js/src/tests/ecma_5/RegExp/shell.js21
16 files changed, 885 insertions, 0 deletions
diff --git a/js/src/tests/ecma_5/RegExp/15.10.5-01.js b/js/src/tests/ecma_5/RegExp/15.10.5-01.js
new file mode 100644
index 000000000..2f8429218
--- /dev/null
+++ b/js/src/tests/ecma_5/RegExp/15.10.5-01.js
@@ -0,0 +1,21 @@
+/*
+ * Any copyright is dedicated to the Public Domain.
+ * http://creativecommons.org/licenses/publicdomain/
+ */
+
+var BUGNUMBER = 614603;
+var summary = "RegExp.length";
+
+print(BUGNUMBER + ": " + summary);
+
+/**************
+ * BEGIN TEST *
+ **************/
+
+assertEq(RegExp.length, 2);
+assertEq(/a/.constructor.length, 2);
+
+if (typeof reportCompare === "function")
+ reportCompare(true, true);
+
+print("All tests passed!");
diff --git a/js/src/tests/ecma_5/RegExp/15.10.7.5-01.js b/js/src/tests/ecma_5/RegExp/15.10.7.5-01.js
new file mode 100644
index 000000000..ab9d071a7
--- /dev/null
+++ b/js/src/tests/ecma_5/RegExp/15.10.7.5-01.js
@@ -0,0 +1,71 @@
+/*
+ * Any copyright is dedicated to the Public Domain.
+ * http://creativecommons.org/licenses/publicdomain/
+ */
+
+var BUGNUMBER = 465199;
+var summary = "RegExp lastIndex property set should not coerce type to number";
+
+print(BUGNUMBER + ": " + summary);
+
+/**************
+ * BEGIN TEST *
+ **************/
+
+var called = false;
+var o = { valueOf: function() { called = true; return 1; } };
+var r = /a/g;
+var desc, m;
+
+assertEq(r.lastIndex, 0);
+
+desc = Object.getOwnPropertyDescriptor(r, "lastIndex");
+assertEq(desc.enumerable, false);
+assertEq(desc.configurable, false);
+assertEq(desc.value, 0);
+assertEq(desc.writable, true);
+
+r.lastIndex = o;
+
+assertEq(r.lastIndex, o);
+
+desc = Object.getOwnPropertyDescriptor(r, "lastIndex");
+assertEq(desc.enumerable, false);
+assertEq(desc.configurable, false);
+assertEq(desc.value, o);
+assertEq(desc.writable, true);
+
+assertEq(called, false);
+assertEq(r.exec("aaaa").length, 1);
+assertEq(called, true);
+assertEq(r.lastIndex, 2);
+
+desc = Object.getOwnPropertyDescriptor(r, "lastIndex");
+assertEq(desc.enumerable, false);
+assertEq(desc.configurable, false);
+assertEq(desc.value, 2);
+assertEq(desc.writable, true);
+
+
+r.lastIndex = -0.2;
+assertEq(r.lastIndex, -0.2);
+
+m = r.exec("aaaa");
+assertEq(Array.isArray(m), true);
+assertEq(m.length, 1);
+assertEq(m[0], "a");
+assertEq(r.lastIndex, 1);
+
+m = r.exec("aaaa");
+assertEq(Array.isArray(m), true);
+assertEq(m.length, 1);
+assertEq(m[0], "a");
+assertEq(r.lastIndex, 2);
+
+
+/******************************************************************************/
+
+if (typeof reportCompare === "function")
+ reportCompare(true, true);
+
+print("All tests passed!");
diff --git a/js/src/tests/ecma_5/RegExp/7.8.5-01.js b/js/src/tests/ecma_5/RegExp/7.8.5-01.js
new file mode 100644
index 000000000..be09bbc14
--- /dev/null
+++ b/js/src/tests/ecma_5/RegExp/7.8.5-01.js
@@ -0,0 +1,35 @@
+/*
+ * Any copyright is dedicated to the Public Domain.
+ * http://creativecommons.org/licenses/publicdomain/
+ */
+
+var BUGNUMBER = 615070;
+var summary = "Line terminator after backslash is invalid in regexp literals";
+
+print(BUGNUMBER + ": " + summary);
+
+/**************
+ * BEGIN TEST *
+ **************/
+
+var regexps = ["/\\\u000A/", "/\\\u000D/", "/\\\u2028/", "/\\\u2029/",
+ "/ab\\\n/", "/ab\\\r/", "/ab\\\u2028/", "/ab\\\u2029/",
+ "/ab[c\\\n]/", "/a[bc\\", "/\\"];
+
+for(var i=0; i<regexps.length; i++) {
+ var src = regexps[i];
+ try {
+ x = eval(src).source;
+ } catch(e) {
+ assertEq(e.constructor, SyntaxError);
+ continue;
+ }
+ assertEq(0, 1);
+}
+
+/**************/
+
+if (typeof reportCompare === "function")
+ reportCompare(true, true);
+
+print("All tests passed!");
diff --git a/js/src/tests/ecma_5/RegExp/browser.js b/js/src/tests/ecma_5/RegExp/browser.js
new file mode 100644
index 000000000..e69de29bb
--- /dev/null
+++ b/js/src/tests/ecma_5/RegExp/browser.js
diff --git a/js/src/tests/ecma_5/RegExp/empty-lookahead.js b/js/src/tests/ecma_5/RegExp/empty-lookahead.js
new file mode 100644
index 000000000..6e2f709e8
--- /dev/null
+++ b/js/src/tests/ecma_5/RegExp/empty-lookahead.js
@@ -0,0 +1,8 @@
+//bug 473941
+var regexp;
+
+regexp = /(?=)/;
+assertEq(regexp.test('test'), true);
+
+if (typeof reportCompare === "function")
+ reportCompare(true, true);
diff --git a/js/src/tests/ecma_5/RegExp/exec-lastIndex-ToInteger.js b/js/src/tests/ecma_5/RegExp/exec-lastIndex-ToInteger.js
new file mode 100644
index 000000000..4505362d8
--- /dev/null
+++ b/js/src/tests/ecma_5/RegExp/exec-lastIndex-ToInteger.js
@@ -0,0 +1,36 @@
+/*
+ * Any copyright is dedicated to the Public Domain.
+ * http://creativecommons.org/licenses/publicdomain/
+ *
+ * Author: Geoffrey Sneddon <geoffers+mozilla@gmail.com>
+ */
+
+var BUGNUMBER = 646490;
+var summary =
+ "RegExp.prototype.exec doesn't get the lastIndex and ToInteger() it for " +
+ "non-global regular expressions when it should";
+
+print(BUGNUMBER + ": " + summary);
+
+/**************
+ * BEGIN TEST *
+ **************/
+
+var re = /./, called = 0;
+re.lastIndex = {valueOf: function() { called++; return 0; }};
+re.exec(".");
+re.lastIndex = {toString: function() { called++; return "0"; }};
+re.exec(".");
+re.lastIndex = {
+ valueOf: function() { called++; return 0; },
+ toString: function() { called--; }
+};
+re.exec(".");
+assertEq(called, 3, "FAIL, got " + called);
+
+/******************************************************************************/
+
+if (typeof reportCompare === "function")
+ reportCompare(true, true);
+
+print("All tests passed!");
diff --git a/js/src/tests/ecma_5/RegExp/exec.js b/js/src/tests/ecma_5/RegExp/exec.js
new file mode 100644
index 000000000..411f348d9
--- /dev/null
+++ b/js/src/tests/ecma_5/RegExp/exec.js
@@ -0,0 +1,240 @@
+/*
+ * Any copyright is dedicated to the Public Domain.
+ * http://creativecommons.org/licenses/publicdomain/
+ */
+
+var BUGNUMBER = 646490;
+var summary =
+ "RegExp.prototype.exec doesn't get the lastIndex and ToInteger() it for " +
+ "non-global regular expressions when it should";
+
+print(BUGNUMBER + ": " + summary);
+
+/**************
+ * BEGIN TEST *
+ **************/
+
+function expectThrowTypeError(fun)
+{
+ try
+ {
+ var r = fun();
+ throw new Error("didn't throw TypeError, returned " + r);
+ }
+ catch (e)
+ {
+ assertEq(e instanceof TypeError, true,
+ "didn't throw TypeError, got: " + e);
+ }
+}
+
+function checkExec(description, regex, args, obj)
+{
+ var lastIndex = obj.lastIndex;
+ var index = obj.index;
+ var input = obj.input;
+ var indexArray = obj.indexArray;
+
+ var res = regex.exec.apply(regex, args);
+
+ assertEq(Array.isArray(res), true, description + ": not an array");
+ assertEq(regex.lastIndex, lastIndex, description + ": wrong lastIndex");
+ assertEq(res.index, index, description + ": wrong index");
+ assertEq(res.input, input, description + ": wrong input");
+ assertEq(res.length, indexArray.length, description + ": wrong length");
+ for (var i = 0, sz = indexArray.length; i < sz; i++)
+ assertEq(res[i], indexArray[i], description + " " + i + ": wrong index value");
+}
+
+var exec = RegExp.prototype.exec;
+var r, res, called, obj;
+
+/* 1. Let R be this RegExp object. */
+expectThrowTypeError(function() { exec.call(null); });
+expectThrowTypeError(function() { exec.call(""); });
+expectThrowTypeError(function() { exec.call(5); });
+expectThrowTypeError(function() { exec.call({}); });
+expectThrowTypeError(function() { exec.call([]); });
+expectThrowTypeError(function() { exec.call(); });
+expectThrowTypeError(function() { exec.call(true); });
+expectThrowTypeError(function() { exec.call(Object.create(RegExp.prototype)); });
+expectThrowTypeError(function() { exec.call(Object.create(/a/)); });
+
+
+/* 2. Let S be the value of ToString(string). */
+called = false;
+r = /a/;
+assertEq(r.lastIndex, 0);
+
+checkExec("/a/", r, [{ toString: function() { called = true; return 'ba'; } }],
+ { lastIndex: 0,
+ index: 1,
+ input: "ba",
+ indexArray: ["a"] });
+assertEq(called, true);
+
+called = false;
+try
+{
+ res = r.exec({ toString: null, valueOf: function() { called = true; throw 17; } });
+ throw new Error("didn't throw");
+}
+catch (e)
+{
+ assertEq(e, 17);
+}
+
+assertEq(called, true);
+
+called = false;
+obj = r.lastIndex = { valueOf: function() { assertEq(true, false, "shouldn't have been called"); } };
+try
+{
+ res = r.exec({ toString: null, valueOf: function() { assertEq(called, false); called = true; throw 17; } });
+ throw new Error("didn't throw");
+}
+catch (e)
+{
+ assertEq(e, 17);
+}
+
+assertEq(called, true);
+assertEq(r.lastIndex, obj);
+
+// We don't test lack of an argument because of RegExp statics non-standard
+// behaviors overriding what really should happen for lack of an argument, sigh.
+
+
+/*
+ * 3. Let length be the length of S.
+ * 4. Let lastIndex be the result of calling the [[Get]] internal method of R with argument "lastIndex".
+ * 5. Let i be the value of ToInteger(lastIndex).
+ */
+r = /b/;
+r.lastIndex = { valueOf: {}, toString: {} };
+expectThrowTypeError(function() { r.exec("foopy"); });
+r.lastIndex = { valueOf: function() { throw new TypeError(); } };
+expectThrowTypeError(function() { r.exec("foopy"); });
+
+
+/*
+ * 6. Let global be the result of calling the [[Get]] internal method of R with argument "global".
+ * 7. If global is false, then let i = 0.
+ */
+obj = { valueOf: function() { return 5; } };
+r = /abc/;
+r.lastIndex = obj;
+
+checkExec("/abc/ take one", r, ["abc-------abc"],
+ { lastIndex: obj,
+ index: 0,
+ input: "abc-------abc",
+ indexArray: ["abc"] });
+
+checkExec("/abc/ take two", r, ["abc-------abc"],
+ { lastIndex: obj,
+ index: 0,
+ input: "abc-------abc",
+ indexArray: ["abc"] });
+
+
+/*
+ * 8. Let matchSucceeded be false.
+ * 9. Repeat, while matchSucceeded is false
+ * a. If i < 0 or i > length, then
+ * i. Call the [[Put]] internal method of R with arguments "lastIndex", 0, and true.
+ * ii. Return null.
+ * b. Call the [[Match]] internal method of R with arguments S and i.
+ * c. If [[Match]] returned failure, then
+ * i. Let i = i+1.
+ * d. else
+ * i. Let r be the State result of the call to [[Match]].
+ * ii. Set matchSucceeded to true.
+ * e. Let i = i+1.
+ */
+r = /abc()?/;
+r.lastIndex = -5;
+checkExec("/abc()?/ with lastIndex -5", r, ["abc-------abc"],
+ { lastIndex: -5,
+ index: 0,
+ input: "abc-------abc",
+ indexArray: ["abc", undefined] });
+
+
+r = /abc/;
+r.lastIndex = -17;
+res = r.exec("cdefg");
+assertEq(res, null);
+assertEq(r.lastIndex, 0);
+
+r = /abc/g;
+r.lastIndex = -42;
+res = r.exec("cdefg");
+assertEq(res, null);
+assertEq(r.lastIndex, 0);
+
+
+/*
+ * 10. Let e be r's endIndex value.
+ * 11. If global is true,
+ * a. Call the [[Put]] internal method of R with arguments "lastIndex", e, and true.
+ */
+r = /abc/g;
+r.lastIndex = 17;
+assertEq(r.exec("sdfs"), null);
+assertEq(r.lastIndex, 0);
+
+r = /abc/g;
+r.lastIndex = 2;
+checkExec("/abc/g", r, ["00abc"],
+ { lastIndex: 5,
+ index: 2,
+ input: "00abc",
+ indexArray: ["abc"] });
+
+
+
+r = /a(b)c/g;
+r.lastIndex = 2;
+checkExec("/a(b)c/g take two", r, ["00abcd"],
+ { lastIndex: 5,
+ index: 2,
+ input: "00abcd",
+ indexArray: ["abc", "b"] });
+
+
+/*
+ * 12. Let n be the length of r's captures array. (This is the same value as
+ * 15.10.2.1's NCapturingParens.)
+ * 13. Let A be a new array created as if by the expression new Array() where
+ * Array is the standard built-in constructor with that name.
+ * 14. Let matchIndex be the position of the matched substring within the
+ * complete String S.
+ * 15. Call the [[DefineOwnProperty]] internal method of A with arguments
+ * "index", Property Descriptor {[[Value]]: matchIndex, [[Writable]: true,
+ * [[Enumerable]]: true, [[Configurable]]: true}, and true.
+ * 16. Call the [[DefineOwnProperty]] internal method of A with arguments
+ * "input", Property Descriptor {[[Value]]: S, [[Writable]: true,
+ * [[Enumerable]]: true, [[Configurable]]: true}, and true.
+ * 17. Call the [[DefineOwnProperty]] internal method of A with arguments
+ * "length", Property Descriptor {[[Value]]: n + 1}, and true.
+ * 18. Let matchedSubstr be the matched substring (i.e. the portion of S
+ * between offset i inclusive and offset e exclusive).
+ * 19. Call the [[DefineOwnProperty]] internal method of A with arguments "0",
+ * Property Descriptor {[[Value]]: matchedSubstr, [[Writable]: true,
+ * [[Enumerable]]: true, [[Configurable]]: true}, and true.
+ * 20. For each integer i such that I > 0 and I ≤ n
+ * a. Let captureI be i th element of r's captures array.
+ * b. Call the [[DefineOwnProperty]] internal method of A with arguments
+ * ToString(i), Property Descriptor {[[Value]]: captureI, [[Writable]:
+ * true, [[Enumerable]]: true, [[Configurable]]: true}, and true.
+ * 21. Return A.
+ */
+// throughout, above (and in other tests)
+
+/******************************************************************************/
+
+if (typeof reportCompare === "function")
+ reportCompare(true, true);
+
+print("All tests passed!");
diff --git a/js/src/tests/ecma_5/RegExp/instance-property-storage-introspection.js b/js/src/tests/ecma_5/RegExp/instance-property-storage-introspection.js
new file mode 100644
index 000000000..1f7c7042f
--- /dev/null
+++ b/js/src/tests/ecma_5/RegExp/instance-property-storage-introspection.js
@@ -0,0 +1,131 @@
+/*
+ * Any copyright is dedicated to the Public Domain.
+ * http://creativecommons.org/licenses/publicdomain/
+ */
+
+var BUGNUMBER = 640072;
+var summary =
+ "Represent /a/.{lastIndex,global,source,multiline,sticky,ignoreCase} with " +
+ "plain old data properties";
+
+print(BUGNUMBER + ": " + summary);
+
+/**************
+ * BEGIN TEST *
+ **************/
+
+function checkDataProperty(obj, p, expect, msg)
+{
+ var d = Object.getOwnPropertyDescriptor(obj, p);
+
+ assertEq(d.value, expect.value, msg + ": bad value for " + p);
+ assertEq(d.writable, expect.writable, msg + ": bad writable for " + p);
+ assertEq(d.enumerable, expect.enumerable, msg + ": bad enumerable for " + p);
+ assertEq(d.configurable, expect.configurable, msg + ": bad configurable for " + p);
+
+ // Try redefining the property using its initial values: these should all be
+ // silent no-ops.
+ Object.defineProperty(obj, p, { value: expect.value });
+ Object.defineProperty(obj, p, { writable: expect.writable });
+ Object.defineProperty(obj, p, { enumerable: expect.enumerable });
+ Object.defineProperty(obj, p, { configurable: expect.configurable });
+
+ var d2 = Object.getOwnPropertyDescriptor(obj, p);
+ assertEq(d.value, d2.value, msg + ": value changed on redefinition of " + p + "?");
+ assertEq(d.writable, d2.writable, msg + ": writable changed on redefinition of " + p + "?");
+ assertEq(d.enumerable, d2.enumerable, msg + ": enumerable changed on redefinition of " + p + "?");
+ assertEq(d.configurable, d2.configurable, msg + ": configurable changed on redefinition of " + p + "?");
+}
+
+
+// Check a bunch of "empty" regular expressions first.
+
+var choices = [{ msg: "RegExp.prototype",
+ get: function() { return RegExp.prototype; } },
+ { msg: "new RegExp()",
+ get: function() { return new RegExp(); } },
+ { msg: "/(?:)/",
+ get: Function("return /(?:)/;") }];
+
+function checkRegExp(r, msg, lastIndex)
+{
+ var expect;
+
+ expect = { value: lastIndex, enumerable: false, configurable: false, writable: true };
+ checkDataProperty(r, "lastIndex", expect, msg);
+}
+
+checkRegExp(RegExp.prototype, "RegExp.prototype", 0);
+checkRegExp(new RegExp(), "new RegExp()", 0);
+checkRegExp(/(?:)/, "/(?:)/", 0);
+checkRegExp(Function("return /(?:)/;")(), 'Function("return /(?:)/;")()', 0);
+
+for (var i = 0; i < choices.length; i++)
+{
+ var choice = choices[i];
+ var msg = choice.msg;
+ var r = choice.get();
+
+ checkRegExp(r, msg, 0);
+}
+
+// Now test less generic regular expressions
+
+checkRegExp(/a/gim, "/a/gim", 0);
+
+var r;
+
+do
+{
+ r = /abcd/mg;
+ checkRegExp(r, "/abcd/mg initially", 0);
+ r.exec("abcdefg");
+ checkRegExp(r, "/abcd/mg step 1", 4);
+ r.exec("abcdabcd");
+ checkRegExp(r, "/abcd/mg step 2", 8);
+ r.exec("abcdabcd");
+ checkRegExp(r, "/abcd/mg end", 0);
+
+ r = /cde/ig;
+ checkRegExp(r, "/cde/ig initially", 0);
+ var obj = r.lastIndex = { valueOf: function() { return 2; } };
+ checkRegExp(r, "/cde/ig after lastIndex", obj);
+ r.exec("aaacdef");
+ checkRegExp(r, "/cde/ig after exec", 6);
+ Object.defineProperty(r, "lastIndex", { value: 3 });
+ checkRegExp(r, "/cde/ig after define 3", 3);
+ Object.defineProperty(r, "lastIndex", { value: obj });
+ checkRegExp(r, "/cde/ig after lastIndex", obj);
+
+
+ // Tricky bits of testing: make sure that redefining lastIndex doesn't change
+ // the slot where the lastIndex property is initially stored, even if
+ // the redefinition also changes writability.
+ r = /a/g;
+ checkRegExp(r, "/a/g initially", 0);
+ Object.defineProperty(r, "lastIndex", { value: 2 });
+ r.exec("aabbbba");
+ checkRegExp(r, "/a/g after first exec", 7);
+ assertEq(r.lastIndex, 7);
+ r.lastIndex = 2;
+ checkRegExp(r, "/a/g after assign", 2);
+ r.exec("aabbbba");
+ assertEq(r.lastIndex, 7); // check in reverse order
+ checkRegExp(r, "/a/g after second exec", 7);
+
+ r = /c/g;
+ r.lastIndex = 2;
+ checkRegExp(r, "/c/g initially", 2);
+ Object.defineProperty(r, "lastIndex", { writable: false });
+ assertEq(Object.getOwnPropertyDescriptor(r, "lastIndex").writable, false);
+ try { r.exec("aabbbba"); } catch (e) { /* swallow error if thrown */ }
+ assertEq(Object.getOwnPropertyDescriptor(r, "lastIndex").writable, false);
+}
+while (Math.random() > 17); // fake loop to discourage RegExp object caching
+
+/******************************************************************************/
+
+if (typeof reportCompare === "function")
+ reportCompare(true, true);
+
+print("All tests passed!");
diff --git a/js/src/tests/ecma_5/RegExp/regexp-space-character-class.js b/js/src/tests/ecma_5/RegExp/regexp-space-character-class.js
new file mode 100644
index 000000000..19d79859c
--- /dev/null
+++ b/js/src/tests/ecma_5/RegExp/regexp-space-character-class.js
@@ -0,0 +1,45 @@
+/* -*- indent-tabs-mode: nil; js-indent-level: 2 -*- */
+/* This Source Code Form is subject to the terms of the Mozilla Public
+* License, v. 2.0. If a copy of the MPL was not distributed with this
+* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+var gTestfile = 'regexp-space-character-class.js';
+//-----------------------------------------------------------------------------
+var BUGNUMBER = 514808;
+var summary = 'Correct space character class in regexes';
+var actual = '';
+var expect = '';
+
+
+//-----------------------------------------------------------------------------
+test();
+//-----------------------------------------------------------------------------
+
+function test()
+{
+enterFunc ('test');
+printBugNumber(BUGNUMBER);
+printStatus (summary);
+
+var spaces = [ "\u0009", "\u000b", "\u000c", "\u0020", "\u00a0", "\u1680",
+"\u180e", "\u2000", "\u2001", "\u2002", "\u2003", "\u2004",
+"\u2005", "\u2006", "\u2007", "\u2008", "\u2009", "\u200a",
+"\u202f", "\u205f", "\u3000", "\ufeff" ];
+var line_terminators = [ "\u2028", "\u2029", "\u000a", "\u000d" ];
+var space_chars = [].concat(spaces, line_terminators);
+
+var non_space_chars = [ "\u200b", "\u200c", "\u200d" ];
+
+var chars = [].concat(space_chars, non_space_chars);
+var is_space = [].concat(space_chars.map(function(ch) { return true; }),
+non_space_chars.map(function(ch) { return false; }));
+var expect = is_space.join(',');
+
+var actual = chars.map(function(ch) { return /\s/.test(ch); }).join(',');
+reportCompare(expect, actual, summary);
+
+var actual = chars.map(function(ch) { return /\s/.test(ch); }).join(',');
+reportCompare(expect, actual, summary);
+
+exitFunc ('test');
+}
diff --git a/js/src/tests/ecma_5/RegExp/regress-429241.js b/js/src/tests/ecma_5/RegExp/regress-429241.js
new file mode 100644
index 000000000..a4b588fea
--- /dev/null
+++ b/js/src/tests/ecma_5/RegExp/regress-429241.js
@@ -0,0 +1,200 @@
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+var gTestfile = 'regress-429241.js';
+var BUGNUMBER = 429241;
+var summary = '\\x or \\u followed by too few hex digits';
+var r;
+
+reportCompare(
+ "x",
+ (r = /[\x]+/.exec("\\x\0")) && r[0],
+ "Section 1"
+);
+
+reportCompare(
+ "xy",
+ (r = /[\xy]+/.exec("\\xy\0")) && r[0],
+ "Section 2"
+);
+
+reportCompare(
+ "x0",
+ (r = /[\x0]+/.exec("\\x0\0")) && r[0],
+ "Section 3"
+);
+
+reportCompare(
+ "x0y",
+ (r = /[\x0y]+/.exec("\\x0y\0")) && r[0],
+ "Section 4"
+);
+
+reportCompare(
+ "\0",
+ (r = /[\x00]+/.exec("\\x\0")) && r[0],
+ "Section 5"
+);
+
+reportCompare(
+ "0\0",
+ (r = /[\x000]+/.exec("0\0")) && r[0],
+ "Section 6"
+);
+
+reportCompare(
+ "x",
+ (r = /^\x$/.exec("x")) && r[0],
+ "Section 7"
+);
+
+reportCompare(
+ "xy",
+ (r = /^\xy$/.exec("xy")) && r[0],
+ "Section 8"
+);
+
+reportCompare(
+ "x0",
+ (r = /^\x0$/.exec("x0")) && r[0],
+ "Section 9"
+);
+
+reportCompare(
+ "x0y",
+ (r = /^\x0y$/.exec("x0y")) && r[0],
+ "Section 10"
+);
+
+reportCompare(
+ null,
+ /^\x00$/.exec("\0" + "0"),
+ "Section 11"
+);
+
+reportCompare(
+ "\0" + "0",
+ (r = /^\x000$/.exec("\0" + "0")) && r[0],
+ "Section 12"
+);
+
+reportCompare(
+ "u",
+ (r = /[\u]+/.exec("\\u\0")) && r[0],
+ "Section 13"
+);
+
+reportCompare(
+ "uy",
+ (r = /[\uy]+/.exec("\\uy\0")) && r[0],
+ "Section 14"
+);
+
+reportCompare(
+ "u0",
+ (r = /[\u0]+/.exec("\\u0\0")) && r[0],
+ "Section 15"
+);
+
+reportCompare(
+ "u0",
+ (r = /[\u00]+/.exec("\\u0\0")) && r[0],
+ "Section 16"
+);
+
+reportCompare(
+ "u0",
+ (r = /[\u000]+/.exec("\\u0\0")) && r[0],
+ "Section 17"
+);
+
+reportCompare(
+ "u0y",
+ (r = /[\u0y]+/.exec("\\u0y\0")) && r[0],
+ "Section 18"
+);
+
+reportCompare(
+ "u0y",
+ (r = /[\u00y]+/.exec("\\u0y\0")) && r[0],
+ "Section 19"
+);
+
+reportCompare(
+ "u0y",
+ (r = /[\u000y]+/.exec("\\u0y\0")) && r[0],
+ "Section 20"
+);
+
+reportCompare(
+ "\0",
+ (r = /[\u0000]+/.exec("\\u\0")) && r[0],
+ "Section 21"
+);
+
+reportCompare(
+ "0\0",
+ (r = /[\u00000]+/.exec("0\0")) && r[0],
+ "Section 22"
+);
+
+reportCompare(
+ "u",
+ (r = /^\u$/.exec("u")) && r[0],
+ "Section 23"
+);
+
+reportCompare(
+ "uy",
+ (r = /^\uy$/.exec("uy")) && r[0],
+ "Section 24"
+);
+
+reportCompare(
+ "u0",
+ (r = /^\u0$/.exec("u0")) && r[0],
+ "Section 25"
+);
+
+reportCompare(
+ "u00",
+ (r = /^\u00$/.exec("u00")) && r[0],
+ "Section 26"
+);
+
+reportCompare(
+ "u000",
+ (r = /^\u000$/.exec("u000")) && r[0],
+ "Section 27"
+);
+
+reportCompare(
+ "u0y",
+ (r = /^\u0y$/.exec("u0y")) && r[0],
+ "Section 28"
+);
+
+reportCompare(
+ "u00y",
+ (r = /^\u00y$/.exec("u00y")) && r[0],
+ "Section 29"
+);
+
+reportCompare(
+ "u000y",
+ (r = /^\u000y$/.exec("u000y")) && r[0],
+ "Section 30"
+);
+
+reportCompare(
+ null,
+ /^\u0000$/.exec("\0" + "0"),
+ "Section 31"
+);
+
+reportCompare(
+ "\0" + "0",
+ (r = /^\u00000$/.exec("\0" + "0")) && r[0],
+ "Section 32"
+);
diff --git a/js/src/tests/ecma_5/RegExp/regress-576828.js b/js/src/tests/ecma_5/RegExp/regress-576828.js
new file mode 100644
index 000000000..45e97dc3b
--- /dev/null
+++ b/js/src/tests/ecma_5/RegExp/regress-576828.js
@@ -0,0 +1,8 @@
+var re = /(z\1){3}/;
+var str = 'zzz';
+var actual = re.exec(str);
+var expected = makeExpectedMatch(['zzz', 'z'], 0, str);
+checkRegExpMatch(actual, expected);
+
+if (typeof reportCompare == 'function')
+ reportCompare(true, true);
diff --git a/js/src/tests/ecma_5/RegExp/regress-613820-1.js b/js/src/tests/ecma_5/RegExp/regress-613820-1.js
new file mode 100644
index 000000000..e5e755b24
--- /dev/null
+++ b/js/src/tests/ecma_5/RegExp/regress-613820-1.js
@@ -0,0 +1,9 @@
+/* Back reference is actually a forwards reference. */
+var re = /(\2(a)){2}/;
+var str = 'aaa';
+var actual = re.exec(str);
+var expected = makeExpectedMatch(['aa', 'a', 'a'], 0, str);
+checkRegExpMatch(actual, expected);
+
+if (typeof reportCompare === 'function')
+ reportCompare(true, true);
diff --git a/js/src/tests/ecma_5/RegExp/regress-613820-2.js b/js/src/tests/ecma_5/RegExp/regress-613820-2.js
new file mode 100644
index 000000000..5db7244ba
--- /dev/null
+++ b/js/src/tests/ecma_5/RegExp/regress-613820-2.js
@@ -0,0 +1,9 @@
+/* Resetting of inner capture groups across quantified capturing parens. */
+var re = /(?:(f)(o)(o)|(b)(a)(r))*/;
+var str = 'foobar';
+var actual = re.exec(str);
+var expected = makeExpectedMatch(['foobar', undefined, undefined, undefined, 'b', 'a', 'r'], 0, str);
+checkRegExpMatch(actual, expected);
+
+if (typeof reportCompare === 'function')
+ reportCompare(true, true);
diff --git a/js/src/tests/ecma_5/RegExp/regress-613820-3.js b/js/src/tests/ecma_5/RegExp/regress-613820-3.js
new file mode 100644
index 000000000..126e838ff
--- /dev/null
+++ b/js/src/tests/ecma_5/RegExp/regress-613820-3.js
@@ -0,0 +1,9 @@
+/* Capture group reset to undefined during second iteration, so backreference doesn't see prior result. */
+var re = /(?:^(a)|\1(a)|(ab)){2}/;
+var str = 'aab';
+var actual = re.exec(str);
+var expected = makeExpectedMatch(['aa', undefined, 'a', undefined], 0, str);
+checkRegExpMatch(actual, expected);
+
+if (typeof reportCompare === 'function')
+ reportCompare(true, true);
diff --git a/js/src/tests/ecma_5/RegExp/regress-617935.js b/js/src/tests/ecma_5/RegExp/regress-617935.js
new file mode 100644
index 000000000..3764d81b0
--- /dev/null
+++ b/js/src/tests/ecma_5/RegExp/regress-617935.js
@@ -0,0 +1,42 @@
+// |reftest| skip-if(!xulRuntime.shell&&(Android||xulRuntime.OS=="WINNT")) silentfail
+/*
+ * Any copyright is dedicated to the Public Domain.
+ * http://creativecommons.org/licenses/publicdomain/
+ *
+ * Author: Christian Holler <decoder@own-hero.net>
+ */
+
+expectExitCode(0);
+expectExitCode(5);
+
+/* Length of 32 */
+var foo = "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa";
+
+/* Make len(foo) 32768 */
+for (i = 0; i < 10; ++i) {
+ foo += foo;
+}
+
+/* Add one "a" to cause overflow later */
+foo += "a";
+
+var bar = "bbbbbbbbbbbbbbbb";
+
+/* Make len(bar) 8192 */
+for (i = 0; i < 9; ++i) {
+ bar += bar;
+}
+
+/*
+ * Resulting string should be
+ * len(foo) * len(bar) = (2**10 * 32 + 1) * 8192 = 268443648
+ * which will be larger than the max string length (2**28, or 268435456).
+ */
+try {
+ foo.replace(/[a]/g, bar);
+} catch (e) {
+ reportCompare(e instanceof InternalError, true, "Internal error due to overallocation is ok.");
+}
+reportCompare(true, true, "No crash occurred.");
+
+print("Tests complete");
diff --git a/js/src/tests/ecma_5/RegExp/shell.js b/js/src/tests/ecma_5/RegExp/shell.js
new file mode 100644
index 000000000..0ce9f087d
--- /dev/null
+++ b/js/src/tests/ecma_5/RegExp/shell.js
@@ -0,0 +1,21 @@
+function makeExpectedMatch(arr, index, input) {
+ var expectedMatch = {
+ index: index,
+ input: input,
+ length: arr.length,
+ };
+
+ for (var i = 0; i < arr.length; ++i)
+ expectedMatch[i] = arr[i];
+
+ return expectedMatch;
+}
+
+function checkRegExpMatch(actual, expected) {
+ assertEq(actual.length, expected.length);
+ for (var i = 0; i < actual.length; ++i)
+ assertEq(actual[i], expected[i]);
+
+ assertEq(actual.index, expected.index);
+ assertEq(actual.input, expected.input);
+}