OLD | NEW |
1 // Copyright 2016 the V8 project authors. All rights reserved. | 1 // Copyright 2016 the V8 project authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 // Flags: --expose-wasm --stress-compaction | 5 // Flags: --expose-wasm --stress-compaction |
6 | 6 |
7 load("test/mjsunit/wasm/wasm-constants.js"); | 7 load("test/mjsunit/wasm/wasm-constants.js"); |
8 load("test/mjsunit/wasm/wasm-module-builder.js"); | 8 load("test/mjsunit/wasm/wasm-module-builder.js"); |
9 | 9 |
10 var kPageSize = 0x10000; | 10 var kPageSize = 0x10000; |
| 11 var kV8MaxPages = 16384; |
11 | 12 |
12 function genGrowMemoryBuilder() { | 13 function genGrowMemoryBuilder() { |
13 var builder = new WasmModuleBuilder(); | 14 var builder = new WasmModuleBuilder(); |
14 builder.addFunction("grow_memory", kSig_i_i) | 15 builder.addFunction("grow_memory", kSig_i_i) |
15 .addBody([kExprGetLocal, 0, kExprGrowMemory, kMemoryZero]) | 16 .addBody([kExprGetLocal, 0, kExprGrowMemory, kMemoryZero]) |
16 .exportFunc(); | 17 .exportFunc(); |
17 builder.addFunction("load", kSig_i_i) | 18 builder.addFunction("load", kSig_i_i) |
18 .addBody([kExprGetLocal, 0, kExprI32LoadMem, 0, 0]) | 19 .addBody([kExprGetLocal, 0, kExprI32LoadMem, 0, 0]) |
19 .exportFunc(); | 20 .exportFunc(); |
20 builder.addFunction("store", kSig_i_ii) | 21 builder.addFunction("store", kSig_i_ii) |
(...skipping 14 matching lines...) Expand all Loading... |
35 .addBody([kExprGetLocal, 0, kExprGetLocal, 1, kExprI32StoreMem8, 0, 0, | 36 .addBody([kExprGetLocal, 0, kExprGetLocal, 1, kExprI32StoreMem8, 0, 0, |
36 kExprGetLocal, 1]) | 37 kExprGetLocal, 1]) |
37 .exportFunc(); | 38 .exportFunc(); |
38 return builder; | 39 return builder; |
39 } | 40 } |
40 | 41 |
41 // TODO(gdeepti): Generate tests programatically for all the sizes instead of | 42 // TODO(gdeepti): Generate tests programatically for all the sizes instead of |
42 // current implementation. | 43 // current implementation. |
43 function testGrowMemoryReadWrite32() { | 44 function testGrowMemoryReadWrite32() { |
44 var builder = genGrowMemoryBuilder(); | 45 var builder = genGrowMemoryBuilder(); |
45 builder.addMemory(1, 1, false); | 46 builder.addMemory(1, kV8MaxPages, false); |
46 var module = builder.instantiate(); | 47 var module = builder.instantiate(); |
47 var offset; | 48 var offset; |
48 function peek() { return module.exports.load(offset); } | 49 function peek() { return module.exports.load(offset); } |
49 function poke(value) { return module.exports.store(offset, value); } | 50 function poke(value) { return module.exports.store(offset, value); } |
50 function growMem(pages) { return module.exports.grow_memory(pages); } | 51 function growMem(pages) { return module.exports.grow_memory(pages); } |
51 | 52 |
52 for(offset = 0; offset <= (kPageSize - 4); offset+=4) { | 53 for(offset = 0; offset <= (kPageSize - 4); offset+=4) { |
53 poke(20); | 54 poke(20); |
54 assertEquals(20, peek()); | 55 assertEquals(20, peek()); |
55 } | 56 } |
(...skipping 26 matching lines...) Expand all Loading... |
82 for (offset = 19*kPageSize - 3; offset < 19*kPageSize + 5; offset++) { | 83 for (offset = 19*kPageSize - 3; offset < 19*kPageSize + 5; offset++) { |
83 assertTraps(kTrapMemOutOfBounds, poke); | 84 assertTraps(kTrapMemOutOfBounds, poke); |
84 assertTraps(kTrapMemOutOfBounds, peek); | 85 assertTraps(kTrapMemOutOfBounds, peek); |
85 } | 86 } |
86 } | 87 } |
87 | 88 |
88 testGrowMemoryReadWrite32(); | 89 testGrowMemoryReadWrite32(); |
89 | 90 |
90 function testGrowMemoryReadWrite16() { | 91 function testGrowMemoryReadWrite16() { |
91 var builder = genGrowMemoryBuilder(); | 92 var builder = genGrowMemoryBuilder(); |
92 builder.addMemory(1, 1, false); | 93 builder.addMemory(1, kV8MaxPages, false); |
93 var module = builder.instantiate(); | 94 var module = builder.instantiate(); |
94 var offset; | 95 var offset; |
95 function peek() { return module.exports.load16(offset); } | 96 function peek() { return module.exports.load16(offset); } |
96 function poke(value) { return module.exports.store16(offset, value); } | 97 function poke(value) { return module.exports.store16(offset, value); } |
97 function growMem(pages) { return module.exports.grow_memory(pages); } | 98 function growMem(pages) { return module.exports.grow_memory(pages); } |
98 | 99 |
99 for(offset = 0; offset <= (kPageSize - 2); offset+=2) { | 100 for(offset = 0; offset <= (kPageSize - 2); offset+=2) { |
100 poke(20); | 101 poke(20); |
101 assertEquals(20, peek()); | 102 assertEquals(20, peek()); |
102 } | 103 } |
(...skipping 26 matching lines...) Expand all Loading... |
129 for (offset = 19*kPageSize - 1; offset < 19*kPageSize + 5; offset++) { | 130 for (offset = 19*kPageSize - 1; offset < 19*kPageSize + 5; offset++) { |
130 assertTraps(kTrapMemOutOfBounds, poke); | 131 assertTraps(kTrapMemOutOfBounds, poke); |
131 assertTraps(kTrapMemOutOfBounds, peek); | 132 assertTraps(kTrapMemOutOfBounds, peek); |
132 } | 133 } |
133 } | 134 } |
134 | 135 |
135 testGrowMemoryReadWrite16(); | 136 testGrowMemoryReadWrite16(); |
136 | 137 |
137 function testGrowMemoryReadWrite8() { | 138 function testGrowMemoryReadWrite8() { |
138 var builder = genGrowMemoryBuilder(); | 139 var builder = genGrowMemoryBuilder(); |
139 builder.addMemory(1, 1, false); | 140 builder.addMemory(1, kV8MaxPages, false); |
140 var module = builder.instantiate(); | 141 var module = builder.instantiate(); |
141 var offset; | 142 var offset; |
142 function peek() { return module.exports.load8(offset); } | 143 function peek() { return module.exports.load8(offset); } |
143 function poke(value) { return module.exports.store8(offset, value); } | 144 function poke(value) { return module.exports.store8(offset, value); } |
144 function growMem(pages) { return module.exports.grow_memory(pages); } | 145 function growMem(pages) { return module.exports.grow_memory(pages); } |
145 | 146 |
146 for(offset = 0; offset <= kPageSize - 1; offset++) { | 147 for(offset = 0; offset <= kPageSize - 1; offset++) { |
147 poke(20); | 148 poke(20); |
148 assertEquals(20, peek()); | 149 assertEquals(20, peek()); |
149 } | 150 } |
(...skipping 166 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
316 function growMem(pages) { return module.exports.grow_memory(pages); } | 317 function growMem(pages) { return module.exports.grow_memory(pages); } |
317 // The parameter of grow_memory is unsigned. Therefore -1 stands for | 318 // The parameter of grow_memory is unsigned. Therefore -1 stands for |
318 // UINT32_MIN, which cannot be represented as SMI. | 319 // UINT32_MIN, which cannot be represented as SMI. |
319 assertEquals(-1, growMem(-1)); | 320 assertEquals(-1, growMem(-1)); |
320 }; | 321 }; |
321 | 322 |
322 testGrowMemoryTrapsWithNonSmiInput(); | 323 testGrowMemoryTrapsWithNonSmiInput(); |
323 | 324 |
324 function testGrowMemoryCurrentMemory() { | 325 function testGrowMemoryCurrentMemory() { |
325 var builder = genGrowMemoryBuilder(); | 326 var builder = genGrowMemoryBuilder(); |
326 builder.addMemory(1, 1, false); | 327 builder.addMemory(1, kV8MaxPages, false); |
327 builder.addFunction("memory_size", kSig_i_v) | 328 builder.addFunction("memory_size", kSig_i_v) |
328 .addBody([kExprMemorySize, kMemoryZero]) | 329 .addBody([kExprMemorySize, kMemoryZero]) |
329 .exportFunc(); | 330 .exportFunc(); |
330 var module = builder.instantiate(); | 331 var module = builder.instantiate(); |
331 function growMem(pages) { return module.exports.grow_memory(pages); } | 332 function growMem(pages) { return module.exports.grow_memory(pages); } |
332 function MemSize() { return module.exports.memory_size(); } | 333 function MemSize() { return module.exports.memory_size(); } |
333 assertEquals(1, MemSize()); | 334 assertEquals(1, MemSize()); |
334 assertEquals(1, growMem(1)); | 335 assertEquals(1, growMem(1)); |
335 assertEquals(2, MemSize()); | 336 assertEquals(2, MemSize()); |
336 } | 337 } |
337 | 338 |
338 testGrowMemoryCurrentMemory(); | 339 testGrowMemoryCurrentMemory(); |
339 | 340 |
340 function testGrowMemoryPreservesDataMemOp32() { | 341 function testGrowMemoryPreservesDataMemOp32() { |
341 var builder = genGrowMemoryBuilder(); | 342 var builder = genGrowMemoryBuilder(); |
342 builder.addMemory(1, 1, false); | 343 builder.addMemory(1, kV8MaxPages, false); |
343 var module = builder.instantiate(); | 344 var module = builder.instantiate(); |
344 var offset, val; | 345 var offset, val; |
345 function peek() { return module.exports.load(offset); } | 346 function peek() { return module.exports.load(offset); } |
346 function poke(value) { return module.exports.store(offset, value); } | 347 function poke(value) { return module.exports.store(offset, value); } |
347 function growMem(pages) { return module.exports.grow_memory(pages); } | 348 function growMem(pages) { return module.exports.grow_memory(pages); } |
348 | 349 |
349 for(offset = 0; offset <= (kPageSize - 4); offset+=4) { | 350 for(offset = 0; offset <= (kPageSize - 4); offset+=4) { |
350 poke(100000 - offset); | 351 poke(100000 - offset); |
351 assertEquals(100000 - offset, peek()); | 352 assertEquals(100000 - offset, peek()); |
352 } | 353 } |
353 | 354 |
354 assertEquals(1, growMem(3)); | 355 assertEquals(1, growMem(3)); |
355 | 356 |
356 for(offset = 0; offset <= (kPageSize - 4); offset+=4) { | 357 for(offset = 0; offset <= (kPageSize - 4); offset+=4) { |
357 assertEquals(100000 - offset, peek()); | 358 assertEquals(100000 - offset, peek()); |
358 } | 359 } |
359 } | 360 } |
360 | 361 |
361 testGrowMemoryPreservesDataMemOp32(); | 362 testGrowMemoryPreservesDataMemOp32(); |
362 | 363 |
363 function testGrowMemoryPreservesDataMemOp16() { | 364 function testGrowMemoryPreservesDataMemOp16() { |
364 var builder = genGrowMemoryBuilder(); | 365 var builder = genGrowMemoryBuilder(); |
365 builder.addMemory(1, 1, false); | 366 builder.addMemory(1, kV8MaxPages, false); |
366 var module = builder.instantiate(); | 367 var module = builder.instantiate(); |
367 var offset, val; | 368 var offset, val; |
368 function peek() { return module.exports.load16(offset); } | 369 function peek() { return module.exports.load16(offset); } |
369 function poke(value) { return module.exports.store16(offset, value); } | 370 function poke(value) { return module.exports.store16(offset, value); } |
370 function growMem(pages) { return module.exports.grow_memory(pages); } | 371 function growMem(pages) { return module.exports.grow_memory(pages); } |
371 | 372 |
372 for(offset = 0; offset <= (kPageSize - 2); offset+=2) { | 373 for(offset = 0; offset <= (kPageSize - 2); offset+=2) { |
373 poke(65535 - offset); | 374 poke(65535 - offset); |
374 assertEquals(65535 - offset, peek()); | 375 assertEquals(65535 - offset, peek()); |
375 } | 376 } |
376 | 377 |
377 assertEquals(1, growMem(3)); | 378 assertEquals(1, growMem(3)); |
378 | 379 |
379 for(offset = 0; offset <= (kPageSize - 2); offset+=2) { | 380 for(offset = 0; offset <= (kPageSize - 2); offset+=2) { |
380 assertEquals(65535 - offset, peek()); | 381 assertEquals(65535 - offset, peek()); |
381 } | 382 } |
382 } | 383 } |
383 | 384 |
384 testGrowMemoryPreservesDataMemOp16(); | 385 testGrowMemoryPreservesDataMemOp16(); |
385 | 386 |
386 function testGrowMemoryPreservesDataMemOp8() { | 387 function testGrowMemoryPreservesDataMemOp8() { |
387 var builder = genGrowMemoryBuilder(); | 388 var builder = genGrowMemoryBuilder(); |
388 builder.addMemory(1, 1, false); | 389 builder.addMemory(1, kV8MaxPages, false); |
389 var module = builder.instantiate(); | 390 var module = builder.instantiate(); |
390 var offset, val = 0; | 391 var offset, val = 0; |
391 function peek() { return module.exports.load8(offset); } | 392 function peek() { return module.exports.load8(offset); } |
392 function poke(value) { return module.exports.store8(offset, value); } | 393 function poke(value) { return module.exports.store8(offset, value); } |
393 function growMem(pages) { return module.exports.grow_memory(pages); } | 394 function growMem(pages) { return module.exports.grow_memory(pages); } |
394 | 395 |
395 for(offset = 0; offset <= (kPageSize - 1); offset++, val++) { | 396 for(offset = 0; offset <= (kPageSize - 1); offset++, val++) { |
396 poke(val); | 397 poke(val); |
397 assertEquals(val, peek()); | 398 assertEquals(val, peek()); |
398 if (val == 255) val = 0; | 399 if (val == 255) val = 0; |
399 } | 400 } |
400 | 401 |
401 assertEquals(1, growMem(3)); | 402 assertEquals(1, growMem(3)); |
402 | 403 |
403 val = 0; | 404 val = 0; |
404 | 405 |
405 for(offset = 0; offset <= (kPageSize - 1); offset++, val++) { | 406 for(offset = 0; offset <= (kPageSize - 1); offset++, val++) { |
406 assertEquals(val, peek()); | 407 assertEquals(val, peek()); |
407 if (val == 255) val = 0; | 408 if (val == 255) val = 0; |
408 } | 409 } |
409 } | 410 } |
410 | 411 |
411 testGrowMemoryPreservesDataMemOp8(); | 412 testGrowMemoryPreservesDataMemOp8(); |
412 | 413 |
413 function testGrowMemoryOutOfBoundsOffset() { | 414 function testGrowMemoryOutOfBoundsOffset() { |
414 var builder = genGrowMemoryBuilder(); | 415 var builder = genGrowMemoryBuilder(); |
415 builder.addMemory(1, 1, false); | 416 builder.addMemory(1, kV8MaxPages, false); |
416 var module = builder.instantiate(); | 417 var module = builder.instantiate(); |
417 var offset, val; | 418 var offset, val; |
418 function peek() { return module.exports.load(offset); } | 419 function peek() { return module.exports.load(offset); } |
419 function poke(value) { return module.exports.store(offset, value); } | 420 function poke(value) { return module.exports.store(offset, value); } |
420 function growMem(pages) { return module.exports.grow_memory(pages); } | 421 function growMem(pages) { return module.exports.grow_memory(pages); } |
421 | 422 |
422 offset = 3*kPageSize + 4; | 423 offset = 3*kPageSize + 4; |
423 assertTraps(kTrapMemOutOfBounds, poke); | 424 assertTraps(kTrapMemOutOfBounds, poke); |
424 | 425 |
425 assertEquals(1, growMem(1)); | 426 assertEquals(1, growMem(1)); |
(...skipping 25 matching lines...) Expand all Loading... |
451 kExprI32Const, 29, | 452 kExprI32Const, 29, |
452 kExprGrowMemory, kMemoryZero, | 453 kExprGrowMemory, kMemoryZero, |
453 kExprI32StoreMem, 0, 0xFF, 0xFF, 0xFF, 0x3a | 454 kExprI32StoreMem, 0, 0xFF, 0xFF, 0xFF, 0x3a |
454 ]) | 455 ]) |
455 .exportAs("main"); | 456 .exportAs("main"); |
456 var module = builder.instantiate(); | 457 var module = builder.instantiate(); |
457 assertTraps(kTrapMemOutOfBounds, module.exports.main); | 458 assertTraps(kTrapMemOutOfBounds, module.exports.main); |
458 } | 459 } |
459 | 460 |
460 testGrowMemoryOutOfBoundsOffset2(); | 461 testGrowMemoryOutOfBoundsOffset2(); |
| 462 |
| 463 function testGrowMemoryDeclaredMaxTraps() { |
| 464 var builder = genGrowMemoryBuilder(); |
| 465 builder.addMemory(1, 16, false); |
| 466 var module = builder.instantiate(); |
| 467 function growMem(pages) { return module.exports.grow_memory(pages); } |
| 468 assertEquals(1, growMem(5)); |
| 469 assertEquals(6, growMem(5)); |
| 470 assertEquals(-1, growMem(6)); |
| 471 } |
| 472 |
| 473 testGrowMemoryDeclaredMaxTraps(); |
| 474 |
| 475 function testGrowMemoryDeclaredSpecMaxTraps() { |
| 476 // The spec maximum is higher than the internal V8 maximum. This test only |
| 477 // checks that grow_memory does not grow past the internally defined maximum |
| 478 // to reflect the currentl implementation. |
| 479 var builder = genGrowMemoryBuilder(); |
| 480 var kSpecMaxPages = 65535; |
| 481 builder.addMemory(1, kSpecMaxPages, false); |
| 482 var module = builder.instantiate(); |
| 483 function poke(value) { return module.exports.store(offset, value); } |
| 484 function growMem(pages) { return module.exports.grow_memory(pages); } |
| 485 assertEquals(1, growMem(20)); |
| 486 assertEquals(-1, growMem(kV8MaxPages - 20)); |
| 487 } |
| 488 |
| 489 testGrowMemoryDeclaredSpecMaxTraps(); |
OLD | NEW |