From 5778737d0653f4f93879ad03bf52c0765b1d682b Mon Sep 17 00:00:00 2001 From: Sami Vaarala Date: Sat, 5 Dec 2015 01:30:43 +0200 Subject: [PATCH] Add testcase for out-of-memory unwind (GH-476) --- .../test-dev-outofmemory-unwind-gh476.js | 378 ++++++++++++++++++ 1 file changed, 378 insertions(+) create mode 100644 tests/ecmascript/test-dev-outofmemory-unwind-gh476.js diff --git a/tests/ecmascript/test-dev-outofmemory-unwind-gh476.js b/tests/ecmascript/test-dev-outofmemory-unwind-gh476.js new file mode 100644 index 0000000000..c8aeff6292 --- /dev/null +++ b/tests/ecmascript/test-dev-outofmemory-unwind-gh476.js @@ -0,0 +1,378 @@ +/* + * https://github.com/svaarala/duktape/issues/476 + * + * When running out of memory, a protected call will catch the error and will + * then proceed to unwind the callstack. The callstack unwind process needs + * to copy variable values from value stack to a scope object (for some + * activations). Because the scope object is not preallocated, this process + * requires a memory allocation which may fail. As a result, a protected call + * first correctly catches an out-of-memory error but throws a new error when + * doing the unwind which then makes the protected call unsafe and may cause + * a fatal error. + * + * This testcase demonstrates the issue. You need a command line 'duk' + * executable which has a limited memory pool, e.g. the 'ajduk' example. + * Expect string is for the desktop version with no memory limitations, + * this testcase is intended to be run manually. + */ + +/*=== +outer 100 +inner 100 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 99 +inner 99 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 98 +inner 98 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 97 +inner 97 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 96 +inner 96 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 95 +inner 95 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 94 +inner 94 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 93 +inner 93 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 92 +inner 92 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 91 +inner 91 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 90 +inner 90 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 89 +inner 89 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 88 +inner 88 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 87 +inner 87 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 86 +inner 86 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 85 +inner 85 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 84 +inner 84 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 83 +inner 83 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 82 +inner 82 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 81 +inner 81 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 80 +inner 80 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 79 +inner 79 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 78 +inner 78 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 77 +inner 77 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 76 +inner 76 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 75 +inner 75 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 74 +inner 74 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 73 +inner 73 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 72 +inner 72 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 71 +inner 71 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 70 +inner 70 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 69 +inner 69 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 68 +inner 68 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 67 +inner 67 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 66 +inner 66 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 65 +inner 65 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 64 +inner 64 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 63 +inner 63 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 62 +inner 62 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 61 +inner 61 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 60 +inner 60 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 59 +inner 59 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 58 +inner 58 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 57 +inner 57 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 56 +inner 56 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 55 +inner 55 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 54 +inner 54 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 53 +inner 53 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 52 +inner 52 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 51 +inner 51 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 50 +inner 50 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 49 +inner 49 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 48 +inner 48 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 47 +inner 47 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 46 +inner 46 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 45 +inner 45 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 44 +inner 44 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 43 +inner 43 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 42 +inner 42 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 41 +inner 41 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 40 +inner 40 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 39 +inner 39 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 38 +inner 38 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 37 +inner 37 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 36 +inner 36 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 35 +inner 35 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 34 +inner 34 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 33 +inner 33 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 32 +inner 32 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 31 +inner 31 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 30 +inner 30 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 29 +inner 29 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 28 +inner 28 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 27 +inner 27 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 26 +inner 26 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 25 +inner 25 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 24 +inner 24 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 23 +inner 23 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 22 +inner 22 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 21 +inner 21 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 20 +inner 20 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 19 +inner 19 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 18 +inner 18 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 17 +inner 17 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 16 +inner 16 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 15 +inner 15 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 14 +inner 14 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 13 +inner 13 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 12 +inner 12 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 11 +inner 11 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 10 +inner 10 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 9 +inner 9 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 8 +inner 8 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 7 +inner 7 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 6 +inner 6 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 5 +inner 5 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 4 +inner 4 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 3 +inner 3 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 2 +inner 2 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 1 +inner 1 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +outer 0 +inner 0 +1045 1146 1245 1345 1445 1545 1645 1745 1845 1945 +finished +===*/ + +function recursive(n) { + /* Large register frame and an inner function ensures that when the + * activation unwinds the lexical scope is copied a lot of variables + * which requires the scope object's property table to grow (if not + * pregrown). + */ + var x00 = 100, x01 = 101, x02 = 102, x03 = 103, x04 = 104, x05 = 105, x06 = 106, x07 = 107, x08 = 108, x09 = 109; + var x11 = 110, x11 = 111, x12 = 112, x13 = 113, x14 = 114, x15 = 115, x16 = 116, x17 = 117, x18 = 118, x19 = 119; + var x20 = 120, x21 = 121, x22 = 122, x23 = 123, x24 = 124, x25 = 125, x26 = 126, x27 = 127, x28 = 128, x29 = 129; + var x30 = 130, x31 = 131, x32 = 132, x33 = 133, x34 = 134, x35 = 135, x36 = 136, x37 = 137, x38 = 138, x39 = 139; + var x40 = 140, x41 = 141, x42 = 142, x43 = 143, x44 = 144, x45 = 145, x46 = 146, x47 = 147, x48 = 148, x49 = 149; + var x50 = 150, x51 = 151, x52 = 152, x53 = 153, x54 = 154, x55 = 155, x56 = 156, x57 = 157, x58 = 158, x59 = 159; + var x60 = 160, x61 = 161, x62 = 162, x63 = 163, x64 = 164, x65 = 165, x66 = 166, x67 = 167, x68 = 168, x69 = 169; + var x70 = 170, x71 = 171, x72 = 172, x73 = 173, x74 = 174, x75 = 175, x76 = 176, x77 = 177, x78 = 178, x79 = 179; + var x80 = 180, x81 = 181, x82 = 182, x83 = 183, x84 = 184, x85 = 185, x86 = 186, x87 = 187, x88 = 188, x89 = 189; + var x90 = 190, x91 = 191, x92 = 192, x93 = 193, x94 = 194, x95 = 195, x96 = 196, x97 = 197, x98 = 198, x99 = 199; + + print('outer', n); + + // Inner function currently causes Duktape to save the outer scope. + // Reference all the variables so that they will be kept in unwound + // even if the scope copying is optimized (not in Duktape 1.4.0 yet + // but planned). + function inner() { + print('inner', n); + print(x00 + x01 + x02 + x03 + x04 + x05 + x06 + x07 + x08 + x09, + x11 + x11 + x12 + x13 + x14 + x15 + x16 + x17 + x18 + x19, + x20 + x21 + x22 + x23 + x24 + x25 + x26 + x27 + x28 + x29, + x30 + x31 + x32 + x33 + x34 + x35 + x36 + x37 + x38 + x39, + x40 + x41 + x42 + x43 + x44 + x45 + x46 + x47 + x48 + x49, + x50 + x51 + x52 + x53 + x54 + x55 + x56 + x57 + x58 + x59, + x60 + x61 + x62 + x63 + x64 + x65 + x66 + x67 + x68 + x69, + x70 + x71 + x72 + x73 + x74 + x75 + x76 + x77 + x78 + x79, + x80 + x81 + x82 + x83 + x84 + x85 + x86 + x87 + x88 + x89, + x90 + x91 + x92 + x93 + x94 + x95 + x96 + x97 + x98 + x99); + } + inner(); + + // Recurse until out-of-memory (or out of patience). + if (n > 0) { + recursive(n - 1); + } else { + ; + } +} + +function test() { + recursive(100); +} + +// No try-catch to avoid memory allocations. +test() +print('finished');