diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/fastLong.js | 18 | ||||
-rw-r--r-- | src/jsifier.js | 53 | ||||
-rw-r--r-- | src/library.js | 17 | ||||
-rw-r--r-- | src/library_browser.js | 7 | ||||
-rw-r--r-- | src/library_sdl.js | 50 | ||||
-rw-r--r-- | src/modules.js | 3 | ||||
-rw-r--r-- | src/parseTools.js | 10 | ||||
-rw-r--r-- | src/relooper/Relooper.cpp | 10 | ||||
-rw-r--r-- | src/relooper/test.txt | 108 | ||||
-rw-r--r-- | src/relooper/test2.txt | 12 | ||||
-rw-r--r-- | src/relooper/test3.txt | 34 | ||||
-rw-r--r-- | src/relooper/test4.txt | 24 | ||||
-rw-r--r-- | src/relooper/test5.txt | 46 | ||||
-rw-r--r-- | src/relooper/test6.txt | 12 | ||||
-rw-r--r-- | src/relooper/test_debug.txt | 12 | ||||
-rw-r--r-- | src/relooper/test_fuzz1.txt | 40 | ||||
-rw-r--r-- | src/relooper/test_fuzz2.txt | 10 | ||||
-rw-r--r-- | src/relooper/test_fuzz3.txt | 2 | ||||
-rw-r--r-- | src/relooper/test_fuzz4.txt | 16 | ||||
-rw-r--r-- | src/relooper/test_fuzz5.txt | 82 | ||||
-rw-r--r-- | src/relooper/test_fuzz6.txt | 186 | ||||
-rw-r--r-- | src/relooper/test_inf.txt | 698 | ||||
-rw-r--r-- | src/runtime.js | 6 |
23 files changed, 736 insertions, 720 deletions
diff --git a/src/fastLong.js b/src/fastLong.js index d1ce5d39..4f6efd9f 100644 --- a/src/fastLong.js +++ b/src/fastLong.js @@ -5,12 +5,12 @@ function ___muldsi3($a, $b) { var $1 = 0, $2 = 0, $3 = 0, $6 = 0, $8 = 0, $11 = 0, $12 = 0; $1 = $a & 65535; $2 = $b & 65535; - $3 = Math.imul($2, $1); + $3 = Math.imul($2, $1) | 0; $6 = $a >>> 16; - $8 = ($3 >>> 16) + Math.imul($2, $6) | 0; + $8 = ($3 >>> 16) + (Math.imul($2, $6) | 0) | 0; $11 = $b >>> 16; - $12 = Math.imul($11, $1); - return (tempRet0 = (($8 >>> 16) + Math.imul($11, $6) | 0) + ((($8 & 65535) + $12 | 0) >>> 16) | 0, 0 | ($8 + $12 << 16 | $3 & 65535)) | 0; + $12 = Math.imul($11, $1) | 0; + return (tempRet0 = (($8 >>> 16) + (Math.imul($11, $6) | 0) | 0) + ((($8 & 65535) + $12 | 0) >>> 16) | 0, 0 | ($8 + $12 << 16 | $3 & 65535)) | 0; } function ___divdi3($a$0, $a$1, $b$0, $b$1) { $a$0 = $a$0 | 0; @@ -47,7 +47,7 @@ function ___remdi3($a$0, $a$1, $b$0, $b$1) { $4$0 = _i64Subtract($1$0 ^ $a$0, $1$1 ^ $a$1, $1$0, $1$1) | 0; $4$1 = tempRet0; $6$0 = _i64Subtract($2$0 ^ $b$0, $2$1 ^ $b$1, $2$0, $2$1) | 0; - ___udivmoddi4($4$0, $4$1, $6$0, tempRet0, $rem); + ___udivmoddi4($4$0, $4$1, $6$0, tempRet0, $rem) | 0; $10$0 = _i64Subtract(HEAP32[$rem >> 2] ^ $1$0, HEAP32[$rem + 4 >> 2] ^ $1$1, $1$0, $1$1) | 0; $10$1 = tempRet0; STACKTOP = __stackBase__; @@ -63,8 +63,8 @@ function ___muldi3($a$0, $a$1, $b$0, $b$1) { $y_sroa_0_0_extract_trunc = $b$0; $1$0 = ___muldsi3($x_sroa_0_0_extract_trunc, $y_sroa_0_0_extract_trunc) | 0; $1$1 = tempRet0; - $2 = Math.imul($a$1, $y_sroa_0_0_extract_trunc); - return (tempRet0 = (Math.imul($b$1, $x_sroa_0_0_extract_trunc) + $2 | 0) + $1$1 | $1$1 & 0, 0 | $1$0 & -1) | 0; + $2 = Math.imul($a$1, $y_sroa_0_0_extract_trunc) | 0; + return (tempRet0 = ((Math.imul($b$1, $x_sroa_0_0_extract_trunc) | 0) + $2 | 0) + $1$1 | $1$1 & 0, 0 | $1$0 & -1) | 0; } function ___udivdi3($a$0, $a$1, $b$0, $b$1) { $a$0 = $a$0 | 0; @@ -84,7 +84,7 @@ function ___uremdi3($a$0, $a$1, $b$0, $b$1) { __stackBase__ = STACKTOP; STACKTOP = STACKTOP + 8 | 0; $rem = __stackBase__ | 0; - ___udivmoddi4($a$0, $a$1, $b$0, $b$1, $rem); + ___udivmoddi4($a$0, $a$1, $b$0, $b$1, $rem) | 0; STACKTOP = __stackBase__; return (tempRet0 = HEAP32[$rem + 4 >> 2] | 0, HEAP32[$rem >> 2] | 0) | 0; } @@ -258,7 +258,7 @@ function ___udivmoddi4($a$0, $a$1, $b$0, $b$1, $rem) { $149 = $carry_0203 | $q_sroa_0_1199 << 1; $r_sroa_0_0_insert_insert42$0 = 0 | ($r_sroa_0_1201 << 1 | $q_sroa_1_1198 >>> 31); $r_sroa_0_0_insert_insert42$1 = $r_sroa_0_1201 >>> 31 | $r_sroa_1_1200 << 1 | 0; - _i64Subtract($137$0, $137$1, $r_sroa_0_0_insert_insert42$0, $r_sroa_0_0_insert_insert42$1); + _i64Subtract($137$0, $137$1, $r_sroa_0_0_insert_insert42$0, $r_sroa_0_0_insert_insert42$1) | 0; $150$1 = tempRet0; $151$0 = $150$1 >> 31 | (($150$1 | 0) < 0 ? -1 : 0) << 1; $152 = $151$0 & 1; diff --git a/src/jsifier.js b/src/jsifier.js index faef88d5..ac6c259b 100644 --- a/src/jsifier.js +++ b/src/jsifier.js @@ -14,6 +14,8 @@ var asmLibraryFunctions = []; var SETJMP_LABEL = -1; +var INDENTATION = ' '; + // JSifier function JSify(data, functionsOnly, givenFunctions) { var mainPass = !functionsOnly; @@ -591,13 +593,13 @@ function JSify(data, functionsOnly, givenFunctions) { func.JS += 'function ' + func.ident + '(' + paramIdents.join(', ') + ') {\n'; if (PGO) { - func.JS += ' PGOMonitor.called["' + func.ident + '"] = 1;\n'; + func.JS += INDENTATION + 'PGOMonitor.called["' + func.ident + '"] = 1;\n'; } if (ASM_JS) { // spell out argument types func.params.forEach(function(param) { - func.JS += ' ' + param.ident + ' = ' + asmCoercion(param.ident, param.type) + ';\n'; + func.JS += INDENTATION + param.ident + ' = ' + asmCoercion(param.ident, param.type) + ';\n'; }); // spell out local variables @@ -611,7 +613,7 @@ function JSify(data, functionsOnly, givenFunctions) { i += chunkSize; } for (i = 0; i < chunks.length; i++) { - func.JS += ' var ' + chunks[i].map(function(v) { + func.JS += INDENTATION + 'var ' + chunks[i].map(function(v) { var type = getImplementationType(v); if (!isIllegalType(type) || v.ident.indexOf('$', 1) > 0) { // not illegal, or a broken up illegal return v.ident + ' = ' + asmInitializer(type); //, func.variables[v.ident].impl); @@ -627,7 +629,7 @@ function JSify(data, functionsOnly, givenFunctions) { if (true) { // TODO: optimize away when not needed if (CLOSURE_ANNOTATIONS) func.JS += '/** @type {number} */'; - func.JS += ' var label = 0;\n'; + func.JS += INDENTATION + 'var label = 0;\n'; } if (ASM_JS) { @@ -636,12 +638,12 @@ function JSify(data, functionsOnly, givenFunctions) { hasByVal = hasByVal || param.byVal; }); if (hasByVal) { - func.JS += ' var tempParam = 0;\n'; + func.JS += INDENTATION + 'var tempParam = 0;\n'; } } // Prepare the stack, if we need one. If we have other stack allocations, force the stack to be set up. - func.JS += ' ' + RuntimeGenerator.stackEnter(func.initialStack, func.otherStackAllocations) + ';\n'; + func.JS += INDENTATION + RuntimeGenerator.stackEnter(func.initialStack, func.otherStackAllocations) + ';\n'; // Make copies of by-value params // XXX It is not clear we actually need this. While without this we fail, it does look like @@ -654,7 +656,7 @@ function JSify(data, functionsOnly, givenFunctions) { if (param.byVal) { var type = removePointing(param.type); var typeInfo = Types.types[type]; - func.JS += ' ' + (ASM_JS ? '' : 'var ') + 'tempParam = ' + param.ident + '; ' + param.ident + ' = ' + RuntimeGenerator.stackAlloc(typeInfo.flatSize) + ';' + + func.JS += INDENTATION + (ASM_JS ? '' : 'var ') + 'tempParam = ' + param.ident + '; ' + param.ident + ' = ' + RuntimeGenerator.stackAlloc(typeInfo.flatSize) + ';' + makeCopyValues(param.ident, 'tempParam', typeInfo.flatSize, 'null', null, param.byVal) + ';\n'; } }); @@ -728,12 +730,12 @@ function JSify(data, functionsOnly, givenFunctions) { } ret += 'switch(' + asmCoercion('label', 'i32') + ') {\n'; ret += block.labels.map(function(label) { - return indent + ' case ' + getLabelId(label.ident) + ': ' + (SHOW_LABELS ? '// ' + getOriginalLabelId(label.ident) : '') + '\n' - + getLabelLines(label, indent + ' '); + return indent + INDENTATION + 'case ' + getLabelId(label.ident) + ': ' + (SHOW_LABELS ? '// ' + getOriginalLabelId(label.ident) : '') + '\n' + + getLabelLines(label, indent + INDENTATION + INDENTATION); }).join('\n') + '\n'; if (func.setjmpTable && ASM_JS) { // emit a label in which we write to the proper local variable, before jumping to the actual label - ret += ' case ' + SETJMP_LABEL + ': '; + ret += INDENTATION + 'case ' + SETJMP_LABEL + ': '; ret += func.setjmpTable.map(function(triple) { // original label, label we created for right after the setjmp, variable setjmp result goes into return 'if ((setjmpLabel|0) == ' + getLabelId(triple.oldLabel) + ') { ' + triple.assignTo + ' = threwValue; label = ' + triple.newLabel + ' }\n'; }).join(' else '); @@ -741,7 +743,7 @@ function JSify(data, functionsOnly, givenFunctions) { ret += '__THREW__ = threwValue = 0;\n'; ret += 'break;\n'; } - if (ASSERTIONS) ret += indent + ' default: assert(0' + (ASM_JS ? '' : ', "bad label: " + label') + ');\n'; + if (ASSERTIONS) ret += indent + INDENTATION + 'default: assert(0' + (ASM_JS ? '' : ', "bad label: " + label') + ');\n'; ret += indent + '}\n'; if (func.setjmpTable && !ASM_JS) { ret += ' } catch(e) { if (!e.longjmp || !(e.id in mySetjmpIds)) throw(e); setjmpTable[setjmpLabels[e.id]](e.value) }'; @@ -797,13 +799,13 @@ function JSify(data, functionsOnly, givenFunctions) { } return ret; } - func.JS += walkBlock(func.block, ' '); + func.JS += walkBlock(func.block, INDENTATION); // Finalize function if (LABEL_DEBUG && functionNameFilterTest(func.ident)) func.JS += " INDENT = INDENT.substr(0, INDENT.length-2);\n"; // Ensure a return in a function with a type that returns, even if it lacks a return (e.g., if it aborts()) if (RELOOP && func.lines.length > 0 && func.returnType != 'void') { var returns = func.labels.filter(function(label) { return label.lines[label.lines.length-1].intertype == 'return' }).length; - if (returns == 0) func.JS += ' return ' + asmCoercion('0', func.returnType); + if (returns == 0) func.JS += INDENTATION + 'return ' + asmCoercion('0', func.returnType); } func.JS += '}\n'; @@ -1121,7 +1123,7 @@ function JSify(data, functionsOnly, givenFunctions) { ret += value + '{\n'; } var phiSet = getPhiSetsForLabel(phiSets, targetLabel); - ret += ' ' + phiSet + makeBranch(targetLabel, item.currLabelId || null) + '\n'; + ret += INDENTATION + '' + phiSet + makeBranch(targetLabel, item.currLabelId || null) + '\n'; ret += '}\n'; if (RELOOP) { item.groupedLabels.push({ @@ -1178,15 +1180,20 @@ function JSify(data, functionsOnly, givenFunctions) { // in an assignment var disabled = DISABLE_EXCEPTION_CATCHING == 2 && !(item.funcData.ident in EXCEPTION_CATCHING_WHITELIST); var phiSets = calcPhiSets(item); - var call_ = makeFunctionCall(item.ident, item.params, item.funcData, item.type, ASM_JS && !disabled); + var call_ = makeFunctionCall(item.ident, item.params, item.funcData, item.type, ASM_JS && !disabled, !!item.assignTo || !item.standalone); var ret; if (disabled) { ret = call_ + ';'; } else if (ASM_JS) { + if (item.type != 'void') call_ = asmCoercion(call_, item.type); // ensure coercion to ffi in comma operator call_ = call_.replace('; return', ''); // we auto-add returns when aborting, but do not need them here - ret = '(__THREW__ = 0,' + call_ + ');'; + if (item.type == 'void') { + ret = '__THREW__ = 0;' + call_ + ';'; + } else { + ret = '(__THREW__ = 0,' + call_ + ');'; + } } else { ret = '(function() { try { __THREW__ = 0; return ' + call_ + ' ' @@ -1310,8 +1317,10 @@ function JSify(data, functionsOnly, givenFunctions) { assert(TARGET_LE32); var ident = item.value.ident; var move = Runtime.STACK_ALIGN; - return '(tempInt=' + makeGetValue(ident, 4, '*') + ',' + - makeSetValue(ident, 4, 'tempInt + ' + move, '*') + ',' + + + // store current list offset in tempInt, advance list offset by STACK_ALIGN, return list entry stored at tempInt + return '(tempInt=' + makeGetValue(ident, Runtime.QUANTUM_SIZE, '*') + ',' + + makeSetValue(ident, Runtime.QUANTUM_SIZE, 'tempInt + ' + move, '*') + ',' + makeGetValue(makeGetValue(ident, 0, '*'), 'tempInt', item.type) + ')'; }); @@ -1328,7 +1337,7 @@ function JSify(data, functionsOnly, givenFunctions) { return ret; }); - function makeFunctionCall(ident, params, funcData, type, forceByPointer) { + function makeFunctionCall(ident, params, funcData, type, forceByPointer, hasReturn) { // We cannot compile assembly. See comment in intertyper.js:'Call' assert(ident != 'asm', 'Inline assembly cannot be compiled to JavaScript!'); @@ -1456,8 +1465,8 @@ function JSify(data, functionsOnly, givenFunctions) { } } - var returnType; - if (byPointer || ASM_JS) { + var returnType = 'void'; + if ((byPointer || ASM_JS) && hasReturn) { returnType = getReturnType(type); } @@ -1502,7 +1511,7 @@ function JSify(data, functionsOnly, givenFunctions) { makeFuncLineActor('getelementptr', function(item) { return finalizeLLVMFunctionCall(item) }); makeFuncLineActor('call', function(item) { if (item.standalone && LibraryManager.isStubFunction(item.ident)) return ';'; - return makeFunctionCall(item.ident, item.params, item.funcData, item.type) + (item.standalone ? ';' : ''); + return makeFunctionCall(item.ident, item.params, item.funcData, item.type, false, !!item.assignTo || !item.standalone) + (item.standalone ? ';' : ''); }); makeFuncLineActor('unreachable', function(item) { diff --git a/src/library.js b/src/library.js index 151cf3e5..01a67804 100644 --- a/src/library.js +++ b/src/library.js @@ -4399,7 +4399,7 @@ LibraryManager.library = { {{{ makeSetValueAsm('dest', 0, makeGetValueAsm('src', 0, 'i8'), 'i8') }}}; } } else { - _memcpy(dest, src, num); + _memcpy(dest, src, num) | 0; } }, llvm_memmove_i32: 'memmove', @@ -4999,22 +4999,19 @@ LibraryManager.library = { return makeSetValue(ptr, 0, 'varrp', 'void*'); #endif #if TARGET_LE32 - // 4-word structure: start, current offset - return makeSetValue(ptr, 0, 'varrp', 'void*') + ';' + makeSetValue(ptr, 4, 0, 'void*'); + // 2-word structure: struct { void* start; void* currentOffset; } + return makeSetValue(ptr, 0, 'varrp', 'void*') + ';' + makeSetValue(ptr, Runtime.QUANTUM_SIZE, 0, 'void*'); #endif }, llvm_va_end: function() {}, llvm_va_copy: function(ppdest, ppsrc) { + // copy the list start {{{ makeCopyValues('ppdest', 'ppsrc', Runtime.QUANTUM_SIZE, 'null', null, 1) }}}; - /* Alternate implementation that copies the actual DATA; it assumes the va_list is prefixed by its size - var psrc = IHEAP[ppsrc]-1; - var num = IHEAP[psrc]; // right before the data, is the number of (flattened) values - var pdest = _malloc(num+1); - _memcpy(pdest, psrc, num+1); - IHEAP[ppdest] = pdest+1; - */ + + // copy the list's current offset (will be advanced with each call to va_arg) + {{{ makeCopyValues('(ppdest+'+Runtime.QUANTUM_SIZE+')', '(ppsrc+'+Runtime.QUANTUM_SIZE+')', Runtime.QUANTUM_SIZE, 'null', null, 1) }}}; }, llvm_bswap_i16: function(x) { diff --git a/src/library_browser.js b/src/library_browser.js index 04c8951d..d007d9a7 100644 --- a/src/library_browser.js +++ b/src/library_browser.js @@ -47,8 +47,11 @@ mergeInto(LibraryManager.library, { workers: [], init: function() { - if (Browser.initted) return; + if (!Module["preloadPlugins"]) Module["preloadPlugins"] = []; // needs to exist even in workers + + if (Browser.initted || ENVIRONMENT_IS_WORKER) return; Browser.initted = true; + try { new Blob(); Browser.hasBlobConstructor = true; @@ -79,8 +82,6 @@ mergeInto(LibraryManager.library, { }[name.substr(name.lastIndexOf('.')+1)]; } - if (!Module["preloadPlugins"]) Module["preloadPlugins"] = []; - var imagePlugin = {}; imagePlugin['canHandle'] = function(name) { return !Module.noImageDecoding && /\.(jpg|jpeg|png|bmp)$/.exec(name); diff --git a/src/library_sdl.js b/src/library_sdl.js index 5aaddb3b..176a2fae 100644 --- a/src/library_sdl.js +++ b/src/library_sdl.js @@ -242,7 +242,7 @@ var LibrarySDL = { }, translateColorToCSSRGBA: function(rgba) { - return 'rgba(' + ((rgba >> 24)&255) + ',' + ((rgba >> 16)&255) + ',' + ((rgba >> 8)&255) + ',' + ((rgba&255)/255) + ')'; + return 'rgba(' + (rgba&0xff) + ',' + (rgba>>8 & 0xff) + ',' + (rgba>>16 & 0xff) + ',' + (rgba>>>24)/0xff + ')'; }, translateRGBAToCSSRGBA: function(r, g, b, a) { @@ -250,7 +250,7 @@ var LibrarySDL = { }, translateRGBAToColor: function(r, g, b, a) { - return (r << 24) + (g << 16) + (b << 8) + a; + return r | g << 8 | b << 16 | a << 24; }, makeSurface: function(width, height, flags, usePageCanvas, source, rmask, gmask, bmask, amask) { @@ -819,7 +819,6 @@ var LibrarySDL = { if (surfData.isFlagSet(0x00200000 /* SDL_HWPALETTE */)) { SDL.copyIndexedColorData(surfData); } else if (!surfData.colors) { - var num = surfData.image.data.length; var data = surfData.image.data; var buffer = surfData.buffer; #if USE_TYPED_ARRAYS == 2 @@ -827,17 +826,14 @@ var LibrarySDL = { var src = buffer >> 2; var dst = 0; var isScreen = surf == SDL.screen; + var data32 = new Uint32Array(data.buffer); + var num = data32.length; while (dst < num) { - // TODO: access underlying data buffer and write in 32-bit chunks or more - var val = HEAP32[src]; // This is optimized. Instead, we could do {{{ makeGetValue('buffer', 'dst', 'i32') }}}; - data[dst ] = val & 0xff; - data[dst+1] = (val >> 8) & 0xff; - data[dst+2] = (val >> 16) & 0xff; - data[dst+3] = isScreen ? 0xff : ((val >> 24) & 0xff); - src++; - dst += 4; + // HEAP32[src++] is an optimization. Instead, we could do {{{ makeGetValue('buffer', 'dst', 'i32') }}}; + data32[dst++] = HEAP32[src++] | (isScreen ? 0xff000000 : 0); } #else + var num = surfData.image.data.length; for (var i = 0; i < num; i++) { // We may need to correct signs here. Potentially you can hardcode a write of 255 to alpha, say, and // the compiler may decide to write -1 in the llvm bitcode... @@ -1120,13 +1116,13 @@ var LibrarySDL = { }, SDL_MapRGB: function(fmt, r, g, b) { - // Canvas screens are always RGBA - return 0xff+((b&0xff)<<8)+((g&0xff)<<16)+((r&0xff)<<24) + // Canvas screens are always RGBA. We assume the machine is little-endian. + return r&0xff|(g&0xff)<<8|(b&0xff)<<16|0xff000000; }, SDL_MapRGBA: function(fmt, r, g, b, a) { - // Canvas screens are always RGBA - return (a&0xff)+((b&0xff)<<8)+((g&0xff)<<16)+((r&0xff)<<24) + // Canvas screens are always RGBA. We assume the machine is little-endian. + return r&0xff|(g&0xff)<<8|(b&0xff)<<16|(a&0xff)<<24; }, SDL_GetAppState: function() { @@ -1389,26 +1385,28 @@ var LibrarySDL = { // If the user asks us to allocate a channel automatically, get the first // free one. if (channel == -1) { - channel = SDL.channelMinimumNumber; for (var i = SDL.channelMinimumNumber; i < SDL.numChannels; i++) { if (!SDL.channels[i].audio) { channel = i; break; } } + if (channel == -1) { + Module.printErr('All ' + SDL.numChannels + ' channels in use!'); + return -1; + } } - // We clone the audio node to utilize the preloaded audio buffer, since // the browser has already preloaded the audio file. var channelInfo = SDL.channels[channel]; channelInfo.audio = audio = audio.cloneNode(true); audio.numChannels = info.audio.numChannels; audio.frequency = info.audio.frequency; - // TODO: handle N loops. Behavior matches Mix_PlayMusic audio.loop = loops != 0; - if (SDL.channelFinished) { - audio['onended'] = function() { // TODO: cache these + audio['onended'] = function() { // TODO: cache these + channelInfo.audio = null; + if (SDL.channelFinished) { Runtime.getFuncWrapper(SDL.channelFinished, 'vi')(channel); } } @@ -1465,7 +1463,6 @@ var LibrarySDL = { audio.play(); } audio.volume = channelInfo.volume; - audio.paused = false; return channel; }, Mix_PlayChannelTimed: 'Mix_PlayChannel', // XXX ignore Timing @@ -1479,6 +1476,8 @@ var LibrarySDL = { if (info.audio) { info.audio.pause(); info.audio = null; + } else { + Module.printErr('No Audio for channel: ' + channel); } if (SDL.channelFinished) { Runtime.getFuncWrapper(SDL.channelFinished, 'vi')(channel); @@ -1516,6 +1515,12 @@ var LibrarySDL = { } audio.volume = SDL.music.volume; audio['onended'] = _Mix_HaltMusic; // will send callback + if (SDL.music.audio) { + if (!SDL.music.audio.paused) { + Module.printErr('Music is already playing. ' + SDL.music.source); + } + SDL.music.audio.pause(); + } SDL.music.audio = audio; return 0; }, @@ -1581,7 +1586,8 @@ var LibrarySDL = { var info = SDL.channels[channel]; if (info && info.audio) { info.audio.pause(); - info.audio.paused = true; + } else { + Module.printErr('Mix_Pause: no sound found for channel: ' + channel); } }, diff --git a/src/modules.js b/src/modules.js index b13ab3c5..d26acbd5 100644 --- a/src/modules.js +++ b/src/modules.js @@ -114,7 +114,8 @@ var Debugging = { m = metadataToParentMetadata[m]; assert(m, 'Confused as to parent metadata for llvm #' + l + ', metadata !' + m); } - this.llvmLineToSourceFile[l] = metadataToFilename[m]; + // Normalize Windows path slashes coming from LLVM metadata, so that forward slashes can be assumed as path delimiters. + this.llvmLineToSourceFile[l] = metadataToFilename[m].replace(/\\5C/g, '/'); } this.on = true; diff --git a/src/parseTools.js b/src/parseTools.js index 687faaa8..0b83a12b 100644 --- a/src/parseTools.js +++ b/src/parseTools.js @@ -710,9 +710,9 @@ function splitI64(value, floatConversion) { var lowInput = legalizedI64s ? value : 'VALUE'; if (floatConversion && ASM_JS) lowInput = asmFloatToInt(lowInput); if (legalizedI64s) { - return [lowInput + '>>>0', 'Math.min(Math.floor((' + value + ')/' + asmEnsureFloat(4294967296, 'float') + '), ' + asmEnsureFloat(4294967295, 'float') + ')>>>0']; + return [lowInput + '>>>0', asmCoercion('Math.min(' + asmCoercion('Math.floor((' + value + ')/' + asmEnsureFloat(4294967296, 'float') + ')', 'double') + ', ' + asmEnsureFloat(4294967295, 'float') + ')', 'i32') + '>>>0']; } else { - return makeInlineCalculation(makeI64(lowInput + '>>>0', 'Math.min(Math.floor(VALUE/' + asmEnsureFloat(4294967296, 'float') + '), ' + asmEnsureFloat(4294967295, 'float') + ')>>>0'), value, 'tempBigIntP'); + return makeInlineCalculation(makeI64(lowInput + '>>>0', asmCoercion('Math.min(' + asmCoercion('Math.floor(VALUE/' + asmEnsureFloat(4294967296, 'float') + ')', 'double') + ', ' + asmEnsureFloat(4294967295, 'float') + ')', 'i32') + '>>>0'), value, 'tempBigIntP'); } } function mergeI64(value, unsigned) { @@ -1049,7 +1049,7 @@ function getHeapOffset(offset, type, forceAsm) { offset = '(' + offset + ')'; if (shifts != 0) { if (CHECK_HEAP_ALIGN) { - return '(CHECK_ALIGN_' + sz + '(' + offset + '|0)>>' + shifts + ')'; + return '((CHECK_ALIGN_' + sz + '(' + offset + '|0)|0)>>' + shifts + ')'; } else { return '(' + offset + '>>' + shifts + ')'; } @@ -1383,7 +1383,7 @@ function makeCopyValues(dest, src, num, type, modifier, align, sep) { if (!isNumber(num)) num = stripCorrections(num); if (!isNumber(align)) align = stripCorrections(align); if (!isNumber(num) || (parseInt(num)/align >= UNROLL_LOOP_MAX)) { - return '_memcpy(' + dest + ', ' + src + ', ' + num + ')'; + return '(_memcpy(' + dest + ', ' + src + ', ' + num + ')|0)'; } num = parseInt(num); if (ASM_JS) { @@ -1465,7 +1465,7 @@ function getFastValue(a, op, b, type) { if ((isNumber(a) && Math.abs(a) < TWO_TWENTY) || (isNumber(b) && Math.abs(b) < TWO_TWENTY) || (bits < 32 && !ASM_JS)) { return '(((' + a + ')*(' + b + '))&' + ((Math.pow(2, bits)-1)|0) + ')'; // keep a non-eliminatable coercion directly on this } - return 'Math.imul(' + a + ',' + b + ')'; + return '(Math.imul(' + a + ',' + b + ')|0)'; } } else { if (a == '0') { diff --git a/src/relooper/Relooper.cpp b/src/relooper/Relooper.cpp index 7ceeb2f8..aa7e71a1 100644 --- a/src/relooper/Relooper.cpp +++ b/src/relooper/Relooper.cpp @@ -18,6 +18,8 @@ static void PrintDebug(const char *Format, ...); #define DebugDump(x, ...) #endif +#define INDENTATION 1 + struct Indenter { static int CurrIndent; @@ -34,8 +36,8 @@ static int OutputBufferSize = 0; void PrintIndented(const char *Format, ...) { assert(OutputBuffer); - assert(OutputBuffer + Indenter::CurrIndent*2 - OutputBufferRoot < OutputBufferSize); - for (int i = 0; i < Indenter::CurrIndent*2; i++, OutputBuffer++) *OutputBuffer = ' '; + assert(OutputBuffer + Indenter::CurrIndent*INDENTATION - OutputBufferRoot < OutputBufferSize); + for (int i = 0; i < Indenter::CurrIndent*INDENTATION; i++, OutputBuffer++) *OutputBuffer = ' '; va_list Args; va_start(Args, Format); int left = OutputBufferSize - (OutputBuffer - OutputBufferRoot); @@ -47,8 +49,8 @@ void PrintIndented(const char *Format, ...) { void PutIndented(const char *String) { assert(OutputBuffer); - assert(OutputBuffer + Indenter::CurrIndent*2 - OutputBufferRoot < OutputBufferSize); - for (int i = 0; i < Indenter::CurrIndent*2; i++, OutputBuffer++) *OutputBuffer = ' '; + assert(OutputBuffer + Indenter::CurrIndent*INDENTATION - OutputBufferRoot < OutputBufferSize); + for (int i = 0; i < Indenter::CurrIndent*INDENTATION; i++, OutputBuffer++) *OutputBuffer = ' '; int left = OutputBufferSize - (OutputBuffer - OutputBufferRoot); int needed = strlen(String)+1; assert(needed < left); diff --git a/src/relooper/test.txt b/src/relooper/test.txt index b3535592..6c910846 100644 --- a/src/relooper/test.txt +++ b/src/relooper/test.txt @@ -6,11 +6,11 @@ // block A if (check == 10) { - atob(); - // block B - btoc(); + atob(); + // block B + btoc(); } else { - atoc(); + atoc(); } // block C @@ -22,9 +22,9 @@ if (check == 10) { // block A if (check == 15) { - // block B + // block B } else { - // block C + // block C } // block D @@ -35,12 +35,12 @@ if (check == 15) { while(1) { - // block A - var check = maybe(); - // block B - if (!(check == 41)) { - break; - } + // block A + var check = maybe(); + // block B + if (!(check == 41)) { + break; + } } // block C @@ -51,25 +51,25 @@ while(1) { // code 1 var $i_0 = 0;var $x_0 = 5; while(1) { - // code 2 - if (!($2)) { - var $x_1 = $x_0; - label = 18; - break; - } - // code 3 - if ($6) { - break; - } else { - var $i_0 = $7;var $x_0 = $5; - } + // code 2 + if (!($2)) { + var $x_1 = $x_0; + label = 18; + break; + } + // code 3 + if ($6) { + break; + } else { + var $i_0 = $7;var $x_0 = $5; + } } if (label == 18) { - // code 7 + // code 7 } // code 4 if ($10) { - // code 5 + // code 5 } // code 6 var $x_1 = $13; @@ -83,15 +83,15 @@ var $x_1 = $13; // block A................................................................................................... if (chak()) { - atob(); - // block B................................................................................................... - btod(); - // block D + atob(); + // block B................................................................................................... + btod(); + // block D } else { - atoc(); - // block C................................................................................................... - ctod2(); - // block D + atoc(); + // block C................................................................................................... + ctod2(); + // block D } @@ -102,11 +102,11 @@ if (chak()) { // block A if (!(check == 10)) { - return C; + return C; } while(1) { - // block B - // block D + // block B + // block D } @@ -117,23 +117,23 @@ while(1) { // block A do { - if (expensive()) { - label = 33; - } else { - // block B - if (expensive2()) { - label = 33; - break; - } - // block D + if (expensive()) { + label = 33; + } else { + // block B + if (expensive2()) { + label = 33; + break; } + // block D + } } while(0); if (label == 33) { - // block C; + // block C; } while(1) { - // block E - // block F + // block E + // block F } @@ -144,12 +144,12 @@ while(1) { // block A if (shouldLoop()) { - while(1) { - // block B - if (!(moarLoop())) { - break; - } + while(1) { + // block B + if (!(moarLoop())) { + break; } + } } // block C diff --git a/src/relooper/test2.txt b/src/relooper/test2.txt index c77ce491..2f3e5ca1 100644 --- a/src/relooper/test2.txt +++ b/src/relooper/test2.txt @@ -1,12 +1,12 @@ ep do { - if (ep -> LBB1) { - LBB1 - if (!(LBB1 -> LBB2)) { - break; - } - LBB2 + if (ep -> LBB1) { + LBB1 + if (!(LBB1 -> LBB2)) { + break; } + LBB2 + } } while(0); LBB3 diff --git a/src/relooper/test3.txt b/src/relooper/test3.txt index 6049ee48..51199f72 100644 --- a/src/relooper/test3.txt +++ b/src/relooper/test3.txt @@ -1,27 +1,27 @@ ep do { - if (ep -> LBB1) { - LBB1 - if (!(LBB1 -> LBB2)) { - break; - } - LBB2 + if (ep -> LBB1) { + LBB1 + if (!(LBB1 -> LBB2)) { + break; } + LBB2 + } } while(0); LBB3 do { - if (LBB3 -> LBB4) { - LBB4 - if (!(LBB4 -> LBB5)) { - break; - } - while(1) { |