summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--AUTHORS3
-rw-r--r--docs/paper.pdfbin220318 -> 220476 bytes
-rw-r--r--docs/paper.tex10
-rwxr-xr-xemcc4
-rw-r--r--src/analyzer.js78
-rw-r--r--src/compiler.js2
-rw-r--r--src/library.js133
-rw-r--r--src/library_browser.js41
-rw-r--r--src/library_gl.js52
-rw-r--r--src/library_glfw.js29
-rw-r--r--src/library_glut.js41
-rw-r--r--src/library_sdl.js106
-rw-r--r--src/modules.js2
-rw-r--r--src/parseTools.js8
-rw-r--r--src/settings.js6
-rw-r--r--tests/box2d/Benchmark.cpp2
-rw-r--r--tests/cases/trace.ll2
-rw-r--r--tests/nbody-java/nbody_nbody.c16
-rwxr-xr-xtests/runner.py135
-rw-r--r--tools/eliminator/asm-eliminator-test-output.js243
-rw-r--r--tools/eliminator/asm-eliminator-test.js429
-rw-r--r--tools/js-optimizer.js43
-rw-r--r--tools/shared.py4
23 files changed, 1156 insertions, 233 deletions
diff --git a/AUTHORS b/AUTHORS
index eae3d6e6..a7a03780 100644
--- a/AUTHORS
+++ b/AUTHORS
@@ -72,5 +72,8 @@ a license to everyone to use it as detailed in LICENSE.)
* Robert Bragg <robert.bragg@intel.com> (copyright owned by Intel Corporation)
* Sylvestre Ledru <sylvestre@debian.org>
* Tom Fairfield <fairfield@cs.xu.edu>
+* Anthony J. Thibault <ajt@hyperlogic.org>
+* John Allwine <jallwine86@gmail.com>
+* Martin Gerhardy <martin.gerhardy@gmail.com>
diff --git a/docs/paper.pdf b/docs/paper.pdf
index 401162ac..fc8ecf7c 100644
--- a/docs/paper.pdf
+++ b/docs/paper.pdf
Binary files differ
diff --git a/docs/paper.tex b/docs/paper.tex
index 3b8da618..9e460bac 100644
--- a/docs/paper.tex
+++ b/docs/paper.tex
@@ -214,7 +214,7 @@ following simple example of a C program:
int main()
{
int sum = 0;
- for (int i = 1; i < 100; i++)
+ for (int i = 1; i <= 100; i++)
sum += i;
printf("1+...+100=%d\n", sum);
return 0;
@@ -239,7 +239,7 @@ define i32 @main() {
; <label>:2
%3 = load i32* %i, align 4
- %4 = icmp slt i32 %3, 100
+ %4 = icmp sle i32 %3, 100
br i1 %4, label %5, label %12
; <label>:5
@@ -314,7 +314,7 @@ function _main() {
__label__ = 0; break;
case 0:
var $3 = HEAP[$i];
- var $4 = $3 < 100;
+ var $4 = $3 <= 100;
if ($4) { __label__ = 1; break; }
else { __label__ = 2; break; }
case 1:
@@ -594,7 +594,7 @@ function _main() {
$i = 0;
$2$2: while(1) {
var $3 = $i;
- var $4 = $3 < 100;
+ var $4 = $3 <= 100;
if (!($4)) { __label__ = 2; break $2$2; }
var $6 = $i;
var $7 = $sum;
@@ -616,7 +616,7 @@ function K() {
var a, b;
b = a = 0;
a:for(;;) {
- if(!(b < 100)) {
+ if(!(b <= 100)) {
break a
}
a += b;
diff --git a/emcc b/emcc
index 8c528a46..4315219a 100755
--- a/emcc
+++ b/emcc
@@ -167,6 +167,7 @@ Options that are modified or new in %s include:
-O3 As -O2, plus dangerous optimizations that may
break the generated code! This adds
+ -s FORCE_ALIGNED_MEMORY=1
-s DOUBLE_MODE=0
-s PRECISE_I64_MATH=0
--closure 1
@@ -174,7 +175,8 @@ Options that are modified or new in %s include:
This is not recommended at all. A better idea
is to try each of these separately on top of
- -O2 to see what works. See the wiki for more
+ -O2 to see what works. See the wiki and
+ src/settings.js (for the -s options) for more
information.
-s OPTION=VALUE JavaScript code generation option passed
diff --git a/src/analyzer.js b/src/analyzer.js
index 3f9025da..a131406c 100644
--- a/src/analyzer.js
+++ b/src/analyzer.js
@@ -20,6 +20,7 @@ var BRANCH_INVOKE = set('branch', 'invoke');
var LABEL_ENDERS = set('branch', 'return', 'switch');
var SIDE_EFFECT_CAUSERS = set('call', 'invoke', 'atomic');
var UNUNFOLDABLE = set('value', 'structvalue', 'type', 'phiparam');
+var I64_DOUBLE_FLIP = { i64: 'double', double: 'i64' };
// Analyzer
@@ -103,61 +104,81 @@ function analyzer(data, sidePass) {
}
});
- // CastAway - try to remove bitcasts of double to i64, which LLVM sometimes generates unnecessarily
+ // CastAway - try to remove bitcasts of double<-->i64, which LLVM sometimes generates unnecessarily
// (load a double, convert to i64, use as i64).
- // We optimize this by checking if the value is later converted to an i64. If so we create a shadow
- // variable that is a load of an i64, and use that in those places. (As SSA, this is valid, and
+ // We optimize this by checking if there are such bitcasts. If so we create a shadow
+ // variable that is of the other type, and use that in the relevant places. (As SSA, this is valid, and
// variable elimination later will remove the double load if it is no longer needed.)
//
+ // Note that aside from being an optimization, this is needed for correctness in some cases: If code
+ // assumes it can bitcast a double to an i64 and back and forth without loss, that may be violated
+ // due to NaN canonicalization.
substrate.addActor('CastAway', {
processItem: function(item) {
this.forwardItem(item, 'Legalizer');
if (USE_TYPED_ARRAYS != 2) return;
item.functions.forEach(function(func) {
- var changed = false;
+ var has = false;
+ func.labels.forEach(function(label) {
+ var lines = label.lines;
+ for (var i = 0; i < lines.length; i++) {
+ var line = lines[i];
+ if (line.intertype == 'bitcast' && line.type in I64_DOUBLE_FLIP) {
+ has = true;
+ }
+ }
+ });
+ if (!has) return;
+ // there are i64<-->double bitcasts, create shadows for everything
+ var shadowed = {};
func.labels.forEach(function(label) {
- var doubleVars = {};
var lines = label.lines;
var i = 0;
while (i < lines.length) {
+ var lines = label.lines;
var line = lines[i];
- if (line.intertype == 'load' && line.type == 'double') {
- doubleVars[line.assignTo] = i;
- } else if (line.intertype == 'bitcast' && line.type == 'i64' && line.ident in doubleVars) {
- // this is a bitcast of a loaded double into an i64. create shadow var
- var shadow = line.ident + '$$i64doubleSHADOW';
- var loadI = doubleVars[line.ident];
- var load = lines[loadI];
- if (load.pointer.intertype != 'value') { i++; continue } // TODO
- // create shadow
- lines.splice(loadI + 1, 0, { // this element will be legalized in the next phase
+ if (line.intertype == 'load' && line.type in I64_DOUBLE_FLIP) {
+ if (line.pointer.intertype != 'value') { i++; continue } // TODO
+ shadowed[line.assignTo] = 1;
+ var shadow = line.assignTo + '$$SHADOW';
+ var flip = I64_DOUBLE_FLIP[line.type];
+ lines.splice(i + 1, 0, { // if necessary this element will be legalized in the next phase
tokens: null,
indent: 2,
- lineNum: load.lineNum + 0.5,
+ lineNum: line.lineNum + 0.5,
assignTo: shadow,
intertype: 'load',
- pointerType: 'i64*',
- type: 'i64',
- valueType: 'i64',
+ pointerType: flip + '*',
+ type: flip,
+ valueType: flip,
pointer: {
intertype: 'value',
- ident: load.pointer.ident,
- type: 'i64*'
+ ident: line.pointer.ident,
+ type: flip + '*'
},
- align: load.align,
- ident: load.ident
+ align: line.align,
+ ident: line.ident
});
- // use shadow
- line.params[0].ident = shadow;
- line.params[0].type = 'i64';
- line.type2 = 'i64';
// note: no need to update func.lines, it is generated in a later pass
i++;
}
i++;
}
});
+ // use shadows where possible
+ func.labels.forEach(function(label) {
+ var lines = label.lines;
+ for (var i = 0; i < lines.length; i++) {
+ var line = lines[i];
+ if (line.intertype == 'bitcast' && line.type in I64_DOUBLE_FLIP && line.ident in shadowed) {
+ var shadow = line.ident + '$$SHADOW';
+ line.params[0].ident = shadow;
+ line.params[0].type = line.type;
+ line.type2 = line.type;
+ }
+ }
+ });
});
}
});
@@ -233,12 +254,15 @@ function analyzer(data, sidePass) {
var factor = (next - prev)/(4*toAdd.length+3);
for (var k = 0; k < toAdd.length; k++) {
toAdd[k].lineNum = prev + ((k+1)*factor);
+ assert(k == 0 || toAdd[k].lineNum > toAdd[k-1].lineNum);
}
}
function removeAndAdd(lines, i, toAdd) {
var item = lines[i];
interpLines(lines, i, toAdd);
Array.prototype.splice.apply(lines, [i, 1].concat(toAdd));
+ if (i > 0) assert(lines[i].lineNum > lines[i-1].lineNum);
+ if (i + toAdd.length < lines.length) assert(lines[i + toAdd.length - 1].lineNum < lines[i + toAdd.length].lineNum);
return toAdd.length;
}
function legalizeFunctionParameters(params) {
diff --git a/src/compiler.js b/src/compiler.js
index 8b9606f1..94e77e26 100644
--- a/src/compiler.js
+++ b/src/compiler.js
@@ -183,8 +183,8 @@ if (ASM_JS) {
assert(!ALLOW_MEMORY_GROWTH, 'Cannot grow asm.js heap');
assert((TOTAL_MEMORY&(TOTAL_MEMORY-1)) == 0, 'asm.js heap must be power of 2');
}
-assert(!(!NAMED_GLOBALS && BUILD_AS_SHARED_LIB)); // shared libraries must have named globals
assert(!BUILD_AS_SHARED_LIB, 'shared libs are deprecated');
+//assert(!(!NAMED_GLOBALS && BUILD_AS_SHARED_LIB), 'shared libraries must have named globals');
// Output some info and warnings based on settings
diff --git a/src/library.js b/src/library.js
index cfe83c6e..84071b68 100644
--- a/src/library.js
+++ b/src/library.js
@@ -296,74 +296,97 @@ LibraryManager.library = {
if (typeof XMLHttpRequest !== 'undefined') {
if (!ENVIRONMENT_IS_WORKER) throw 'Cannot do synchronous binary XHRs outside webworkers in modern browsers. Use --embed-file or --preload-file in emcc';
// Lazy chunked Uint8Array (implements get and length from Uint8Array). Actual getting is abstracted away for eventual reuse.
- var LazyUint8Array = function(chunkSize, length) {
- this.length = length;
- this.chunkSize = chunkSize;
+ var LazyUint8Array = function() {
+ this.lengthKnown = false;
this.chunks = []; // Loaded chunks. Index is the chunk number
}
LazyUint8Array.prototype.get = function(idx) {
if (idx > this.length-1 || idx < 0) {
return undefined;
}
- var chunkOffset = idx % chunkSize;
- var chunkNum = Math.floor(idx / chunkSize);
+ var chunkOffset = idx % this.chunkSize;
+ var chunkNum = Math.floor(idx / this.chunkSize);
return this.getter(chunkNum)[chunkOffset];
}
LazyUint8Array.prototype.setDataGetter = function(getter) {
this.getter = getter;
}
-
- // Find length
- var xhr = new XMLHttpRequest();
- xhr.open('HEAD', url, false);
- xhr.send(null);
- if (!(xhr.status >= 200 && xhr.status < 300 || xhr.status === 304)) throw new Error("Couldn't load " + url + ". Status: " + xhr.status);
- var datalength = Number(xhr.getResponseHeader("Content-length"));
- var header;
- var hasByteServing = (header = xhr.getResponseHeader("Accept-Ranges")) && header === "bytes";
+
+ LazyUint8Array.prototype.cacheLength = function() {
+ // Find length
+ var xhr = new XMLHttpRequest();
+ xhr.open('HEAD', url, false);
+ xhr.send(null);
+ if (!(xhr.status >= 200 && xhr.status < 300 || xhr.status === 304)) throw new Error("Couldn't load " + url + ". Status: " + xhr.status);
+ var datalength = Number(xhr.getResponseHeader("Content-length"));
+ var header;
+ var hasByteServing = (header = xhr.getResponseHeader("Accept-Ranges")) && header === "bytes";
#if SMALL_XHR_CHUNKS
- var chunkSize = 1024; // Chunk size in bytes
+ var chunkSize = 1024; // Chunk size in bytes
#else
- var chunkSize = 1024*1024; // Chunk size in bytes
+ var chunkSize = 1024*1024; // Chunk size in bytes
#endif
- if (!hasByteServing) chunkSize = datalength;
-
- // Function to get a range from the remote URL.
- var doXHR = (function(from, to) {
- if (from > to) throw new Error("invalid range (" + from + ", " + to + ") or no bytes requested!");
- if (to > datalength-1) throw new Error("only " + datalength + " bytes available! programmer error!");
-
- // TODO: Use mozResponseArrayBuffer, responseStream, etc. if available.
- var xhr = new XMLHttpRequest();
- xhr.open('GET', url, false);
- if (datalength !== chunkSize) xhr.setRequestHeader("Range", "bytes=" + from + "-" + to);
-
- // Some hints to the browser that we want binary data.
- if (typeof Uint8Array != 'undefined') xhr.responseType = 'arraybuffer';
- if (xhr.overrideMimeType) {
- xhr.overrideMimeType('text/plain; charset=x-user-defined');
- }
+ if (!hasByteServing) chunkSize = datalength;
+
+ // Function to get a range from the remote URL.
+ var doXHR = (function(from, to) {
+ if (from > to) throw new Error("invalid range (" + from + ", " + to + ") or no bytes requested!");
+ if (to > datalength-1) throw new Error("only " + datalength + " bytes available! programmer error!");
+
+ // TODO: Use mozResponseArrayBuffer, responseStream, etc. if available.
+ var xhr = new XMLHttpRequest();
+ xhr.open('GET', url, false);
+ if (datalength !== chunkSize) xhr.setRequestHeader("Range", "bytes=" + from + "-" + to);
+
+ // Some hints to the browser that we want binary data.
+ if (typeof Uint8Array != 'undefined') xhr.responseType = 'arraybuffer';
+ if (xhr.overrideMimeType) {
+ xhr.overrideMimeType('text/plain; charset=x-user-defined');
+ }
+
+ xhr.send(null);
+ if (!(xhr.status >= 200 && xhr.status < 300 || xhr.status === 304)) throw new Error("Couldn't load " + url + ". Status: " + xhr.status);
+ if (xhr.response !== undefined) {
+ return new Uint8Array(xhr.response || []);
+ } else {
+ return intArrayFromString(xhr.responseText || '', true);
+ }
+ });
+ var lazyArray = this;
+ lazyArray.setDataGetter(function(chunkNum) {
+ var start = chunkNum * chunkSize;
+ var end = (chunkNum+1) * chunkSize - 1; // including this byte
+ end = Math.min(end, datalength-1); // if datalength-1 is selected, this is the last block
+ if (typeof(lazyArray.chunks[chunkNum]) === "undefined") {
+ lazyArray.chunks[chunkNum] = doXHR(start, end);
+ }
+ if (typeof(lazyArray.chunks[chunkNum]) === "undefined") throw new Error("doXHR failed!");
+ return lazyArray.chunks[chunkNum];
+ });
+
+ this._length = datalength;
+ this._chunkSize = chunkSize;
+ this.lengthKnown = true;
+ }
- xhr.send(null);
- if (!(xhr.status >= 200 && xhr.status < 300 || xhr.status === 304)) throw new Error("Couldn't load " + url + ". Status: " + xhr.status);
- if (xhr.response !== undefined) {
- return new Uint8Array(xhr.response || []);
- } else {
- return intArrayFromString(xhr.responseText || '', true);
- }
+ var lazyArray = new LazyUint8Array();
+ Object.defineProperty(lazyArray, "length", {
+ get: function() {
+ if(!this.lengthKnown) {
+ this.cacheLength();
+ }
+ return this._length;
+ }
});
-
- var lazyArray = new LazyUint8Array(chunkSize, datalength);
- lazyArray.setDataGetter(function(chunkNum) {
- var start = chunkNum * lazyArray.chunkSize;
- var end = (chunkNum+1) * lazyArray.chunkSize - 1; // including this byte
- end = Math.min(end, datalength-1); // if datalength-1 is selected, this is the last block
- if (typeof(lazyArray.chunks[chunkNum]) === "undefined") {
- lazyArray.chunks[chunkNum] = doXHR(start, end);
- }
- if (typeof(lazyArray.chunks[chunkNum]) === "undefined") throw new Error("doXHR failed!");
- return lazyArray.chunks[chunkNum];
+ Object.defineProperty(lazyArray, "chunkSize", {
+ get: function() {
+ if(!this.lengthKnown) {
+ this.cacheLength();
+ }
+ return this._chunkSize;
+ }
});
+
var properties = { isDevice: false, contents: lazyArray };
} else {
var properties = { isDevice: false, url: url };
@@ -2465,9 +2488,15 @@ LibraryManager.library = {
__scanString.whiteSpace[{{{ charCode(' ') }}}] = 1;
__scanString.whiteSpace[{{{ charCode('\t') }}}] = 1;
__scanString.whiteSpace[{{{ charCode('\n') }}}] = 1;
+ __scanString.whiteSpace[{{{ charCode('\v') }}}] = 1;
+ __scanString.whiteSpace[{{{ charCode('\f') }}}] = 1;
+ __scanString.whiteSpace[{{{ charCode('\r') }}}] = 1;
__scanString.whiteSpace[' '] = 1;
__scanString.whiteSpace['\t'] = 1;
__scanString.whiteSpace['\n'] = 1;
+ __scanString.whiteSpace['\v'] = 1;
+ __scanString.whiteSpace['\f'] = 1;
+ __scanString.whiteSpace['\r'] = 1;
}
// Supports %x, %4x, %d.%d, %lld, %s, %f, %lf.
// TODO: Support all format specifiers.
@@ -2840,7 +2869,7 @@ LibraryManager.library = {
} else if (next == {{{ charCode('o') }}}) {
argText = (flagAlternative ? '0' : '') + currAbsArg.toString(8);
} else if (next == {{{ charCode('x') }}} || next == {{{ charCode('X') }}}) {
- prefix = flagAlternative ? '0x' : '';
+ prefix = (flagAlternative && currArg != 0) ? '0x' : '';
#if PRECISE_I64_MATH
if (argSize == 8 && i64Math) {
if (origArg[1]) {
diff --git a/src/library_browser.js b/src/library_browser.js
index 85eb93f7..97233c36 100644
--- a/src/library_browser.js
+++ b/src/library_browser.js
@@ -374,6 +374,47 @@ mergeInto(LibraryManager.library, {
0;
},
+ mouseX: 0,
+ mouseY: 0,
+ mouseMovementX: 0,
+ mouseMovementY: 0,
+
+ calculateMouseEvent: function(event) { // event should be mousemove, mousedown or mouseup
+ if (Browser.pointerLock) {
+ // When the pointer is locked, calculate the coordinates
+ // based on the movement of the mouse.
+ // Workaround for Firefox bug 764498
+ if (event.type != 'mousemove' &&
+ ('mozMovementX' in event)) {
+ Browser.mouseMovementX = Browser.mouseMovementY = 0;
+ } else {
+ Browser.mouseMovementX = Browser.getMovementX(event);
+ Browser.mouseMovementY = Browser.getMovementY(event);
+ }
+ Browser.mouseX = SDL.mouseX + Browser.mouseMovementX;
+ Browser.mouseY = SDL.mouseY + Browser.mouseMovementY;
+ } else {
+ // Otherwise, calculate the movement based on the changes
+ // in the coordinates.
+ var rect = Module["canvas"].getBoundingClientRect();
+ var x = event.pageX - (window.scrollX + rect.left);
+ var y = event.pageY - (window.scrollY + rect.top);
+
+ // the canvas might be CSS-scaled compared to its backbuffer;
+ // SDL-using content will want mouse coordinates in terms
+ // of backbuffer units.
+ var cw = Module["canvas"].width;
+ var ch = Module["canvas"].height;
+ x = x * (cw / rect.width);
+ y = y * (ch / rect.height);
+
+ Browser.mouseMovementX = x - Browser.mouseX;
+ Browser.mouseMovementY = y - Browser.mouseY;
+ Browser.mouseX = x;
+ Browser.mouseY = y;
+ }
+ },
+
xhrLoad: function(url, onload, onerror) {
var xhr = new XMLHttpRequest();
xhr.open('GET', url, true);
diff --git a/src/library_gl.js b/src/library_gl.js
index 813da761..0f6fb670 100644
--- a/src/library_gl.js
+++ b/src/library_gl.js
@@ -339,6 +339,9 @@ var LibraryGL = {
Module.ctx.getExtension('WEBKIT_EXT_texture_filter_anisotropic');
GL.floatExt = Module.ctx.getExtension('OES_texture_float');
+
+ GL.elementIndexUintExt = Module.ctx.getExtension('OES_element_index_uint');
+ GL.standardDerivativesExt = Module.ctx.getExtension('OES_standard_derivatives');
}
},
@@ -781,7 +784,7 @@ var LibraryGL = {
program = GL.programs[program];
var info = Module.ctx.getActiveUniform(program, index);
- var infoname = info.name.slice(0, bufSize - 1);
+ var infoname = info.name.slice(0, Math.max(0, bufSize - 1));
writeStringToMemory(infoname, name);
if (length) {
@@ -795,25 +798,25 @@ var LibraryGL = {
}
},
- glUniform1f__sig: 'vid',
+ glUniform1f__sig: 'vif',
glUniform1f: function(location, v0) {
location = GL.uniforms[location];
Module.ctx.uniform1f(location, v0);
},
- glUniform2f__sig: 'vidd',
+ glUniform2f__sig: 'viff',
glUniform2f: function(location, v0, v1) {
location = GL.uniforms[location];
Module.ctx.uniform2f(location, v0, v1);
},
- glUniform3f__sig: 'viddd',
+ glUniform3f__sig: 'vifff',
glUniform3f: function(location, v0, v1, v2) {
location = GL.uniforms[location];
Module.ctx.uniform3f(location, v0, v1, v2);
},
- glUniform4f__sig: 'vidddd',
+ glUniform4f__sig: 'viffff',
glUniform4f: function(location, v0, v1, v2, v3) {
location = GL.uniforms[location];
Module.ctx.uniform4f(location, v0, v1, v2, v3);
@@ -1031,7 +1034,7 @@ var LibraryGL = {
program = GL.programs[program];
var info = Module.ctx.getActiveAttrib(program, index);
- var infoname = info.name.slice(0, bufSize - 1);
+ var infoname = info.name.slice(0, Math.max(0, bufSize - 1));
writeStringToMemory(infoname, name);
if (length) {
@@ -1058,12 +1061,6 @@ var LibraryGL = {
GL.shaders[shader] = null;
},
- glDetachShader__sig: 'vii',
- glDetachShader: function(program, shader) {
- Module.ctx.detachShader(GL.programs[program],
- GL.shaders[shader]);
- },
-
glGetAttachedShaders__sig: 'viiii',
glGetAttachedShaders: function(program, maxCount, count, shaders) {
var result = Module.ctx.getAttachedShaders(GL.programs[program]);
@@ -1086,7 +1083,7 @@ var LibraryGL = {
glGetShaderSource__sig: 'viiii',
glGetShaderSource: function(shader, bufSize, length, source) {
var result = Module.ctx.getShaderSource(GL.shaders[shader]);
- result = result.slice(0, bufSize - 1);
+ result = result.slice(0, Math.max(0, bufSize - 1));
writeStringToMemory(result, source);
if (length) {
{{{ makeSetValue('length', '0', 'result.length', 'i32') }}};
@@ -1157,6 +1154,12 @@ var LibraryGL = {
GL.shaders[shader]);
},
+ glDetachShader__sig: 'vii',
+ glDetachShader: function(program, shader) {
+ Module.ctx.detachShader(GL.programs[program],
+ GL.shaders[shader]);
+ },
+
glGetShaderPrecisionFormat: function(shaderType, precisionType, range, precision) {
var result = Module.ctx.getShaderPrecisionFormat(shaderType, precisionType);
{{{ makeSetValue('range', '0', 'result.rangeMin', 'i32') }}};
@@ -1194,7 +1197,7 @@ var LibraryGL = {
Module.ctx.validateProgram(GL.programs[program]);
},
- glIsProgram__sig: 'vi',
+ glIsProgram__sig: 'ii',
glIsProgram: function(program) {
var program = GL.programs[program];
if (!program) return 0;
@@ -1583,6 +1586,18 @@ var LibraryGL = {
glAttachShader(program, shader);
};
+ var glDetachShader = _glDetachShader;
+ _glDetachShader = function(program, shader) {
+ var programShader = GL.programShaders[program];
+ if (!programShader) {
+ Module.printErr('WARNING: _glDetachShader received invalid program: ' + program);
+ return;
+ }
+ var index = programShader.indexOf(shader);
+ programShader.splice(index, 1);
+ glDetachShader(program, shader);
+ };
+
var glUseProgram = _glUseProgram;
_glUseProgram = function(program) {
#if GL_DEBUG
@@ -1713,6 +1728,7 @@ var LibraryGL = {
case 'glCreateProgramObject': case 'glCreateProgram': ret = {{{ Functions.getIndex('_glCreateProgram', true) }}}; break;
case 'glAttachObject': case 'glAttachShader': ret = {{{ Functions.getIndex('_glAttachShader', true) }}}; break;
case 'glUseProgramObject': case 'glUseProgram': ret = {{{ Functions.getIndex('_glUseProgram', true) }}}; break;
+ case 'glDetachObject': case 'glDetachShader': ret = {{{ Functions.getIndex('_glDetachShader', true) }}}; break;
case 'glDeleteObject': ret = {{{ Functions.getIndex('_glDeleteObject', true) }}}; break;
case 'glGetObjectParameteriv': ret = {{{ Functions.getIndex('_glGetObjectParameteriv', true) }}}; break;
case 'glGetInfoLog': ret = {{{ Functions.getIndex('_glGetInfoLog', true) }}}; break;
@@ -1786,7 +1802,9 @@ var LibraryGL = {
case 'glGetBufferParameteriv': ret = {{{ Functions.getIndex('_glGetBufferParameteriv', true) }}}; break;
case 'glIsBuffer': ret = {{{ Functions.getIndex('_glIsBuffer', true) }}}; break;
case 'glDeleteShader': ret = {{{ Functions.getIndex('_glDeleteShader', true) }}}; break;
- case 'glUniformMatrix2fv': ret = {{{ Functions.getIndex('_glUniformMatrix2fv', true) }}}; break;
+ case 'glUniformMatrix2fv': ret = {{{ Functions.getIndex('_glUniformMatrix2fv', true) }}}; break;
+ case 'glUniformMatrix3fv': ret = {{{ Functions.getIndex('_glUniformMatrix3fv', true) }}}; break;
+ case 'glUniformMatrix4fv': ret = {{{ Functions.getIndex('_glUniformMatrix4fv', true) }}}; break;
case 'glIsRenderbuffer': ret = {{{ Functions.getIndex('_glIsRenderbuffer', true) }}}; break;
case 'glBlendEquation': ret = {{{ Functions.getIndex('_glBlendEquation', true) }}}; break;
case 'glBlendFunc': ret = {{{ Functions.getIndex('_glBlendFunc', true) }}}; break;
@@ -1900,6 +1918,9 @@ var LibraryGL = {
if (type == 0x8B84) { // GL_OBJECT_INFO_LOG_LENGTH_ARB
{{{ makeSetValue('result', '0', 'Module.ctx.getShaderInfoLog(GL.shaders[id]).length', 'i32') }}};
return;
+ } else if (type == 0x8B88) { // GL_OBJECT_SHADER_SOURCE_LENGTH_ARB
+ {{{ makeSetValue('result', '0', 'Module.ctx.getShaderSource(GL.shaders[id]).length', 'i32') }}};
+ return;
}
_glGetShaderiv(id, type, result);
} else {
@@ -3107,6 +3128,7 @@ var LibraryGL = {
glTexGeni: function() { throw 'glTexGeni: TODO' },
glTexGenfv: function() { throw 'glTexGenfv: TODO' },
glTexEnvi: function() { Runtime.warnOnce('glTexEnvi: TODO') },
+ glTexEnvf: function() { Runtime.warnOnce('glTexEnvf: TODO') },
glTexEnvfv: function() { Runtime.warnOnce('glTexEnvfv: TODO') },
glTexImage1D: function() { throw 'glTexImage1D: TODO' },
diff --git a/src/library_glfw.js b/src/library_glfw.js
index 8bf3616f..5e76071f 100644
--- a/src/library_glfw.js
+++ b/src/library_glfw.js
@@ -35,8 +35,6 @@ var LibraryGLFW = {
params: null,
initTime: null,
wheelPos: 0,
- lastX: 0,
- lastY: 0,
buttons: 0,
keys: 0,
initWindowWidth: 640,
@@ -145,28 +143,20 @@ var LibraryGLFW = {
GLFW.onKeyChanged(event, 0);//GLFW_RELEASE
},
- savePosition: function(event) {
- /* TODO maybe loop here ala http://www.quirksmode.org/js/findpos.html */
- GLFW.lastX = event['clientX'] - Module['canvas'].offsetLeft;
- GLFW.lastY = event['clientY'] - Module['canvas'].offsetTop;
- },
-
onMousemove: function(event) {
/* Send motion event only if the motion changed, prevents
* spamming our app with uncessary callback call. It does happen in
* Chrome on Windows.
*/
- var newX = event['clientX'] - Module['canvas'].offsetLeft;
- var newY = event['clientY'] - Module['canvas'].offsetTop;
- if (newX == GLFW.lastX && newY == GLFW.lastY) {
- return;
- }
-
- GLFW.savePosition(event);
+ var lastX = Browser.mouseX;
+ var lastY = Browser.mouseY;
+ Browser.calculateMouseEvent(event);
+ var newX = Browser.mouseX;
+ var newY = Browser.mouseY;
if (event.target == Module["canvas"] && GLFW.mousePosFunc) {
event.preventDefault();
- Runtime.dynCall('vii', GLFW.mousePosFunc, [GLFW.lastX, GLFW.lastY]);
+ Runtime.dynCall('vii', GLFW.mousePosFunc, [lastX, lastY]);
}
},
@@ -175,7 +165,8 @@ var LibraryGLFW = {
return;
}
- GLFW.savePosition(event);
+ Browser.calculateMouseEvent(event);
+
if (event.target != Module["canvas"]) {
return;
}
@@ -441,8 +432,8 @@ var LibraryGLFW = {
},
glfwGetMousePos: function(xpos, ypos) {
- setValue(xpos, GLFW.lastX, 'i32');
- setValue(ypos, GLFW.lastY, 'i32');
+ setValue(xpos, Browser.mouseX, 'i32');
+ setValue(ypos, Browser.mouseY, 'i32');
},
//I believe it is not possible to move the mouse with javascript
diff --git a/src/library_glut.js b/src/library_glut.js
index 49380367..35348028 100644
--- a/src/library_glut.js
+++ b/src/library_glut.js
@@ -12,8 +12,6 @@ var LibraryGLUT = {
motionFunc: null,
passiveMotionFunc: null,
mouseFunc: null,
- lastX: 0,
- lastY: 0,
buttons: 0,
modifiers: 0,
initWindowWidth: 256,
@@ -24,12 +22,6 @@ var LibraryGLUT = {
windowWidth: 0,
windowHeight: 0,
- savePosition: function(event) {
- /* TODO maybe loop here ala http://www.quirksmode.org/js/findpos.html */
- GLUT.lastX = event['clientX'] - Module['canvas'].offsetLeft;
- GLUT.lastY = event['clientY'] - Module['canvas'].offsetTop;
- },
-
saveModifiers: function(event) {
GLUT.modifiers = 0;
if (event['shiftKey'])
@@ -45,20 +37,21 @@ var LibraryGLUT = {
* spamming our app with uncessary callback call. It does happen in
* Chrome on Windows.
*/
- var newX = event['clientX'] - Module['canvas'].offsetLeft;
- var newY = event['clientY'] - Module['canvas'].offsetTop;
- if (newX == GLUT.lastX && newY == GLUT.lastY)
- return;
+ var lastX = Browser.mouseX;
+ var lastY = Browser.mouseY;
+ Browser.calculateMouseEvent(event);
+ var newX = Browser.mouseX;
+ var newY = Browser.mouseY;
+ if (newX == lastX && newY == lastY) return;
- GLUT.savePosition(event);
if (GLUT.buttons == 0 && event.target == Module["canvas"] && GLUT.passiveMotionFunc) {
event.preventDefault();
GLUT.saveModifiers(event);
- Runtime.dynCall('vii', GLUT.passiveMotionFunc, [GLUT.lastX, GLUT.lastY]);
+ Runtime.dynCall('vii', GLUT.passiveMotionFunc, [lastX, lastY]);
} else if (GLUT.buttons != 0 && GLUT.motionFunc) {
event.preventDefault();
GLUT.saveModifiers(event);
- Runtime.dynCall('vii', GLUT.motionFunc, [GLUT.lastX, GLUT.lastY]);
+ Runtime.dynCall('vii', GLUT.motionFunc, [lastX, lastY]);
}
},
@@ -159,7 +152,7 @@ var LibraryGLUT = {
if( GLUT.specialFunc ) {
event.preventDefault();
GLUT.saveModifiers(event);
- Runtime.dynCall('viii', GLUT.specialFunc, [key, GLUT.lastX, GLUT.lastY]);
+ Runtime.dynCall('viii', GLUT.specialFunc, [key, Browser.mouseX, Browser.mouseY]);
}
}
else
@@ -168,7 +161,7 @@ var LibraryGLUT = {
if( key !== null && GLUT.keyboardFunc ) {
event.preventDefault();
GLUT.saveModifiers(event);
- Runtime.dynCall('viii', GLUT.keyboardFunc, [key, GLUT.lastX, GLUT.lastY]);
+ Runtime.dynCall('viii', GLUT.keyboardFunc, [key, Browser.mouseX, Browser.mouseY]);
}
}
}
@@ -181,7 +174,7 @@ var LibraryGLUT = {
if(GLUT.specialUpFunc) {
event.preventDefault ();
GLUT.saveModifiers(event);
- Runtime.dynCall('viii', GLUT.specialUpFunc, [key, GLUT.lastX, GLUT.lastY]);
+ Runtime.dynCall('viii', GLUT.specialUpFunc, [key, Browser.mouseX, Browser.mouseY]);
}
}
else
@@ -190,14 +183,15 @@ var LibraryGLUT = {
if( key !== null && GLUT.keyboardUpFunc ) {
event.preventDefault ();
GLUT.saveModifiers(event);
- Runtime.dynCall('viii', GLUT.keyboardUpFunc, [key, GLUT.lastX, GLUT.lastY]);
+ Runtime.dynCall('viii', GLUT.keyboardUpFunc, [key, Browser.mouseX, Browser.mouseY]);
}
}
}
},
onMouseButtonDown: function(event){
- GLUT.savePosition(event);
+ Browser.calculateMouseEvent(event);
+
GLUT.buttons |= (1 << event['button']);
if(event.target == Module["canvas"] && GLUT.mouseFunc){
@@ -206,18 +200,19 @@ var LibraryGLUT = {
} catch (e) {}
event.preventDefault();
GLUT.saveModifiers(event);
- Runtime.dynCall('viiii', GLUT.mouseFunc, [event['button'], 0/*GLUT_DOWN*/, GLUT.lastX, GLUT.lastY]);
+ Runtime.dynCall('viiii', GLUT.mouseFunc, [event['button'], 0/*GLUT_DOWN*/, Browser.mouseX, Browser.mouseY]);
}
},
onMouseButtonUp: function(event){
- GLUT.savePosition(event);
+ Browser.calculateMouseEvent(event);
+
GLUT.buttons &= ~(1 << event['button']);
if(GLUT.mouseFunc) {
event.preventDefault();
GLUT.saveModifiers(event);
- Runtime.dynCall('viiii', GLUT.mouseFunc, [event['button'], 1/*GLUT_UP*/, GLUT.lastX, GLUT.lastY]);
+ Runtime.dynCall('viiii', GLUT.mouseFunc, [event['button'], 1/*GLUT_UP*/, Browser.mouseX, Browser.mouseY]);
}
},
diff --git a/src/library_sdl.js b/src/library_sdl.js
index a1fb871f..9c5e9805 100644
--- a/src/library_sdl.js
+++ b/src/library_sdl.js
@@ -46,8 +46,6 @@ var LibrarySDL = {
textInput: false,
startTime: null,
- mouseX: 0,
- mouseY: 0,
buttonState: 0,
DOMButtons: [0, 0, 0],
@@ -515,54 +513,22 @@ var LibrarySDL = {
}
// fall through
case 'mousemove': {
- if (Browser.pointerLock) {
- // When the pointer is locked, calculate the coordinates
- // based on the movement of the mouse.
- // Workaround for Firefox bug 764498
- if (event.type != 'mousemove' &&
- ('mozMovementX' in event)) {
- var movementX = 0, movementY = 0;
- } else {
- var movementX = Browser.getMovementX(event);
- var movementY = Browser.getMovementY(event);
- }
- var x = SDL.mouseX + movementX;
- var y = SDL.mouseY + movementY;
- } else {
- // Otherwise, calculate the movement based on the changes
- // in the coordinates.
- var rect = Module["canvas"].getBoundingClientRect();
- var x = event.pageX - (window.scrollX + rect.left);
- var y = event.pageY - (window.scrollY + rect.top);
-
- // the canvas might be CSS-scaled compared to its backbuffer;
- // SDL-using content will want mouse coordinates in terms
- // of backbuffer units.
- var cw = Module["canvas"].width;
- var ch = Module["canvas"].height;
- x = x * (cw / rect.width);
- y = y * (ch / rect.height);
-
- var movementX = x - SDL.mouseX;
- var movementY = y - SDL.mouseY;
- }
+ Browser.calculateMouseEvent(event);
if (event.type != 'mousemove') {
var down = event.type === 'mousedown';
{{{ makeSetValue('ptr', 'SDL.structs.MouseButtonEvent.type', 'SDL.DOMEventToSDLEvent[event.type]', 'i32') }}};
{{{ makeSetValue('ptr', 'SDL.structs.MouseButtonEvent.button', 'event.button+1', 'i8') }}}; // DOM buttons are 0-2, SDL 1-3
{{{ makeSetValue('ptr', 'SDL.structs.MouseButtonEvent.state', 'down ? 1 : 0', 'i8') }}};
- {{{ makeSetValue('ptr', 'SDL.structs.MouseButtonEvent.x', 'x', 'i32') }}};
- {{{ makeSetValue('ptr', 'SDL.structs.MouseButtonEvent.y', 'y', 'i32') }}};
+ {{{ makeSetValue('ptr', 'SDL.structs.MouseButtonEvent.x', 'Browser.mouseX', 'i32') }}};
+ {{{ makeSetValue('ptr', 'SDL.structs.MouseButtonEvent.y', 'Browser.mouseY', 'i32') }}};
} else {
{{{ makeSetValue('ptr', 'SDL.structs.MouseMotionEvent.type', 'SDL.DOMEventToSDLEvent[event.type]', 'i32') }}};
{{{ makeSetValue('ptr', 'SDL.structs.MouseMotionEvent.state', 'SDL.buttonState', 'i8') }}};
- {{{ makeSetValue('ptr', 'SDL.structs.MouseMotionEvent.x', 'x', 'i32') }}};
- {{{ makeSetValue('ptr', 'SDL.structs.MouseMotionEvent.y', 'y', 'i32') }}};
- {{{ makeSetValue('ptr', 'SDL.structs.MouseMotionEvent.xrel', 'movementX', 'i32') }}};
- {{{ makeSetValue('ptr', 'SDL.structs.MouseMotionEvent.yrel', 'movementY', 'i32') }}};
+ {{{ makeSetValue('ptr', 'SDL.structs.MouseMotionEvent.x', 'Browser.mouseX', 'i32') }}};
+ {{{ makeSetValue('ptr', 'SDL.structs.MouseMotionEvent.y', 'Browser.mouseY', 'i32') }}};
+ {{{ makeSetValue('ptr', 'SDL.structs.MouseMotionEvent.xrel', 'Browser.mouseMovementX', 'i32') }}};
+ {{{ makeSetValue('ptr', 'SDL.structs.MouseMotionEvent.yrel', 'Browser.mouseMovementY', 'i32') }}};
}
- SDL.mouseX = x;
- SDL.mouseY = y;
break;
}
case 'unload': {
@@ -924,8 +890,8 @@ var LibrarySDL = {
},
SDL_GetMouseState: function(x, y) {
- if (x) {{{ makeSetValue('x', '0', 'SDL.mouseX', 'i32') }}};
- if (y) {{{ makeSetValue('y', '0', 'SDL.mouseY', 'i32') }}};
+ if (x) {{{ makeSetValue('x', '0', 'Browser.mouseX', 'i32') }}};
+ if (y) {{{ makeSetValue('y', '0', 'Browser.mouseY', 'i32') }}};
return SDL.buttonState;
},
@@ -1705,6 +1671,60 @@ var LibrarySDL = {
SDL_GL_SwapBuffers: function() {},
+ // SDL 2
+
+ SDL_GL_ExtensionSupported: function(extension) {
+ return Module.ctx.getExtension(extension) | 0;
+ },
+
+ SDL_DestroyWindow: function(window) {},
+
+ SDL_DestroyRenderer: function(renderer) {},
+
+ SDL_GetWindowFlags: function(x, y) {
+ if (Browser.isFullScreen) {
+ return 1;
+ }
+
+ return 0;
+ },
+
+ SDL_GL_SwapWindow: function(window) {},
+
+ SDL_GL_MakeCurrent: function(window, context) {},
+
+ SDL_GL_DeleteContext: function(context) {},
+
+ SDL_GL_SetSwapInterval: function(state) {},
+
+ SDL_SetWindowTitle: function(window, title) {
+ if (title) document.title = Pointer_stringify(title);
+ },
+
+ SDL_GetWindowSize: function(window, width, height){
+ var w = Module['canvas'].width;
+ var h = Module['canvas'].height;
+ if (width) {{{ makeSetValue('width', '0', 'w', 'i32') }}};
+ if (height) {{{ makeSetValue('height', '0', 'h', 'i32') }}};
+ },
+
+ SDL_LogSetOutputFunction: function(callback, userdata) {},
+
+ SDL_SetWindowFullscreen: function(window, fullscreen) {
+ if (Browser.isFullScreen) {
+ Module['canvas'].cancelFullScreen();
+ return 1;
+ } else {
+ return 0;
+ }
+ },
+
+ SDL_GetWindowFlags: function() {},
+
+ SDL_ClearError: function() {},
+
+ SDL_getenv: 'getenv',
+
// TODO
SDL_SetGamma: function(r, g, b) {
diff --git a/src/modules.js b/src/modules.js
index 6b3c5ffb..2775bfbd 100644
--- a/src/modules.js
+++ b/src/modules.js
@@ -305,7 +305,7 @@ var Functions = {
// Resolve multi-level aliases all the way down
while (1) {
var varData = Variables.globals[table[i]];
- if (!(varData && varData.resolvedAlias)) break;
+ if (!(varData && varData.resolvedAlias && varData.resolvedAlias.indexOf('FUNCTION_TABLE_OFFSET') < 0)) break;
table[i] = table[+varData.resolvedAlias || eval(varData.resolvedAlias)]; // might need to eval to turn (6) into 6
}
// Resolve library aliases
diff --git a/src/parseTools.js b/src/parseTools.js
index db834206..fa0f251e 100644
--- a/src/parseTools.js
+++ b/src/parseTools.js
@@ -1118,6 +1118,8 @@ var asmPrintCounter = 0;
// See makeSetValue
function makeGetValue(ptr, pos, type, noNeedFirst, unsigned, ignore, align, noSafe, forceAsm) {
if (UNALIGNED_MEMORY) align = 1;
+ else if (FORCE_ALIGNED_MEMORY && !isIllegalType(type)) align = 8;
+
if (isStructType(type)) {
var typeData = Types.types[type];
var ret = [];
@@ -1220,6 +1222,8 @@ function indexizeFunctions(value, type) {
//! @param noNeedFirst Whether to ignore the offset in the pointer itself.
function makeSetValue(ptr, pos, value, type, noNeedFirst, ignore, align, noSafe, sep, forcedAlign, forceAsm) {
if (UNALIGNED_MEMORY && !forcedAlign) align = 1;
+ else if (FORCE_ALIGNED_MEMORY && !isIllegalType(type)) align = 8;
+
sep = sep || ';';
if (isStructType(type)) {
var typeData = Types.types[type];
@@ -1678,10 +1682,10 @@ function checkBitcast(item) {
function showWarning() {
if (warned) return;
warned = true;
- if (VERBOSE || ASM_JS) {
+ if (VERBOSE) {
warnOnce('Casting potentially incompatible function pointer ' + oldType + ' to ' + newType + ', for ' + item.params[0].ident.slice(1));
} else {
- warnOnce('Casting a function pointer type to a potentially incompatible one (use VERBOSE=1 to see more)');
+ warnOnce('Casting a function pointer type to a potentially incompatible one (use -s VERBOSE=1 to see more)');
}
warnOnce('See https://github.com/kripken/emscripten/wiki/CodeGuidlinesAndLimitations#function-pointer-issues for more information on dangerous function pointer casts');
if (ASM_JS) warnOnce('Incompatible function pointer casts are very dangerous with ASM_JS=1, you should investigate and correct these');
diff --git a/src/settings.js b/src/settings.js
index d029598a..8766277b 100644
--- a/src/settings.js
+++ b/src/settings.js
@@ -89,6 +89,12 @@ var UNALIGNED_MEMORY = 0; // If enabled, all memory accesses are assumed to be u
// typed arrays mode 2 where alignment is relevant.) In unaligned memory mode, you
// can run nonportable code that typically would break in JS (or on ARM for that
// matter, which also cannot do unaligned reads/writes), at the cost of slowness
+var FORCE_ALIGNED_MEMORY = 0; // If enabled, assumes all reads and writes are fully aligned for the type they
+ // use. This is true in proper C code (no undefined behavior), but is sadly
+ // common enough that we can't do it by default. See SAFE_HEAP and CHECK_HEAP_ALIGN
+ // for ways to help find places in your code where unaligned reads/writes are done -
+ // you might be able to refactor your codebase to prevent them, which leads to
+ // smaller and faster code, or even the option to turn this flag on.
var PRECISE_I64_MATH = 1; // If enabled, i64 addition etc. is emulated - which is slow but precise. If disabled,
// we use the 'double trick' which is fast but incurs rounding at high values.
// Note that we do not catch 32-bit multiplication by default (which must be done in
diff --git a/tests/box2d/Benchmark.cpp b/tests/box2d/Benchmark.cpp
index 6853a3dc..0db1d4be 100644
--- a/tests/box2d/Benchmark.cpp
+++ b/tests/box2d/Benchmark.cpp
@@ -31,7 +31,7 @@ using namespace std;
const int e_count = 40;
-result_t measure(clock_t times[FRAMES]) {
+result_t measure(clock_t *times) {
float values[FRAMES];
result_t r;
diff --git a/tests/cases/trace.ll b/tests/cases/trace.ll
index 1bada3e9..ec68ef92 100644
--- a/tests/cases/trace.ll
+++ b/tests/cases/trace.ll
@@ -24,7 +24,7 @@ entry:
%retval = alloca i32, align 4 ; [#uses=1 type=i32*]
store i32 0, i32* %retval
%call = call i32 (i8*, ...)* @printf(i8* getelementptr inbounds ([15 x i8]* @.str, i32 0, i32 0)) ; [#uses=0 type=i32]
- %0 = getelementptr inbounds [4 x %struct.TraceKindPair]* @_ZL14traceKindNames, i32 0, i32 1; [#uses=1 type=%struct.TraceKindPair*] [debug line = 1473:17]
+ %0 = getelementptr inbounds [4 x %struct.TraceKindPair]* @_ZL14traceKindNames, i32 0, i32 1 ; [#uses=1 type=%struct.TraceKindPair*] [debug line = 1473:17]
%1 = getelementptr inbounds %struct.TraceKindPair* %0, i32 0, i32 0 ; [#uses=1 type=i8**] [debug line = 1473:17]
ret i32 1
}
diff --git a/tests/nbody-java/nbody_nbody.c b/tests/nbody-java/nbody_nbody.c
index b6fa9695..4d77bb32 100644
--- a/tests/nbody-java/nbody_nbody.c
+++ b/tests/nbody-java/nbody_nbody.c
@@ -246,6 +246,22 @@ void nbody_nbody_main___java_lang_String_1ARRAY(JAVA_OBJECT n1)
int main(int argc, char* argv[])
{
+ // translate our normalized argument (0-0, 1-0.1secs, 2-0.5secs, 3-1sec, 4-5secs, 5-10secs) to nbody
+ int arg = argc > 1 ? argv[1][0] - '0' : 3;
+ char buffer[100];
+ argv[1] = buffer;
+ int n;
+ switch(arg) {
+ case 0: return 0; break;
+ case 1: n = 600000; break;
+ case 2: n = 3600000; break;
+ case 3: n = 6550000; break;
+ case 4: n = 30000000; break;
+ case 5: n = 60000000; break;
+ default: printf("error: %d\\n", arg); return -1;
+ }
+ snprintf(buffer, 50, "%d", n);
+
xmlvm_init();
// Initialize the main thread before entering XMLVM_SETJMP
diff --git a/tests/runner.py b/tests/runner.py
index 27fb84dc..b2b1ff43 100755
--- a/tests/runner.py
+++ b/tests/runner.py
@@ -291,7 +291,7 @@ process(sys.argv[1])
out = open(stdout, 'r').read()
err = open(stderr, 'r').read()
if engine == SPIDERMONKEY_ENGINE and Settings.ASM_JS:
- if 'Successfully compiled asm.js code' in err and 'asm.js link error' not in err:
+ if 'uccessfully compiled asm.js code' in err and 'asm.js link error' not in err:
print >> sys.stderr, "[was asm.js'ified]"
elif 'asm.js' in err: # if no asm.js error, then not an odin build
raise Exception("did NOT asm.js'ify")
@@ -447,6 +447,8 @@ process(sys.argv[1])
sys.argv = map(lambda arg: arg if not arg.startswith('test_') else 'default.' + arg, sys.argv)
+test_modes = ['default', 'o1', 'o2', 'asm1', 'asm2', 'asm2g', 'asm2x86', 's_0_0', 's_0_1', 's_1_0', 's_1_1']
+
test_index = 0
if 'benchmark' not in str(sys.argv) and 'sanity' not in str(sys.argv) and 'browser' not in str(sys.argv):
@@ -454,10 +456,10 @@ if 'benchmark' not in str(sys.argv) and 'sanity' not in str(sys.argv) and 'brows
print "Running Emscripten tests..."
- if len(sys.argv) == 2 and 'ALL.' in sys.argv[1]:
+ if len(sys.argv) == 2 and sys.argv[1].startswith('ALL.'):
ignore, test = sys.argv[1].split('.')
print 'Running all test modes on test "%s"' % test
- sys.argv = [sys.argv[0], 'default.'+test, 'o1.'+test, 'o2.'+test, 'asm1.'+test, 'asm2.'+test, 'asm2g.'+test, 'asm2x86.'+test, 's_0_0.'+test, 's_0_1.'+test, 's_1_0.'+test, 's_1_1.'+test]
+ sys.argv = [sys.argv[0]] + map(lambda mode: mode+'.'+test, test_modes)
class T(RunnerCore): # Short name, to make it more fun to use manually on the commandline
## Does a complete test - builds, runs, checks output, etc.
@@ -5618,7 +5620,7 @@ at function.:blag
open(path_from_root('tests', 'printf', 'output_i64_1.txt'), 'r').read()]
self.do_run(src, expected)
- def test_printf_types(self):
+ def test_printf_2(self):
src = r'''
#include <stdio.h>
@@ -5631,11 +5633,12 @@ at function.:blag
double d = 6.6;
printf("%c,%hd,%d,%lld,%.1f,%.1llf\n", c, s, i, l, f, d);
+ printf("%#x,%#x\n", 1, 0);
return 0;
}
'''
- self.do_run(src, '1,2,3,4,5.5,6.6\n')
+ self.do_run(src, '1,2,3,4,5.5,6.6\n0x1,0\n')
def test_vprintf(self):
src = r'''
@@ -6039,6 +6042,40 @@ Pass: 0.000012 0.000012''')
'''
self.do_run(src, '''0:173,16 1:16,173 2:183,173 3:17,287 4:98,123''')
+ def test_sscanf_other_whitespace(self):
+ Settings.SAFE_HEAP = 0 # use i16s in printf
+
+ src = r'''
+ #include<stdio.h>
+
+ int main() {
+ short int x;
+ short int y;
+
+ const char* buffer[] = {
+ "\t2\t3\t", /* TAB - horizontal tab */
+ "\t\t5\t\t7\t\t",
+ "\n11\n13\n", /* LF - line feed */
+ "\n\n17\n\n19\n\n",
+ "\v23\v29\v", /* VT - vertical tab */
+ "\v\v31\v\v37\v\v",
+ "\f41\f43\f", /* FF - form feed */
+ "\f\f47\f\f53\f\f",
+ "\r59\r61\r", /* CR - carrage return */
+ "\r\r67\r\r71\r\r"
+ };
+
+ for (int i=0; i<10; ++i) {
+ x = 0; y = 0;
+ sscanf(buffer[i], " %d %d ", &x, &y);
+ printf("%d, %d, ", x, y);
+ }
+
+ return 0;
+ }
+ '''
+ self.do_run(src, '''2, 3, 5, 7, 11, 13, 17, 19, 23, 29, 31, 37, 41, 43, 47, 53, 59, 61, 67, 71, ''')
+
def test_sscanf_3(self):
# i64
if not Settings.USE_TYPED_ARRAYS == 2: return self.skip('64-bit sscanf only supported in ta2')
@@ -7832,15 +7869,29 @@ def process(filename):
Settings.SAFE_HEAP_LINES = ['btVoronoiSimplexSolver.h:40', 'btVoronoiSimplexSolver.h:41',
'btVoronoiSimplexSolver.h:42', 'btVoronoiSimplexSolver.h:43']
- self.do_run(open(path_from_root('tests', 'bullet', 'Demos', 'HelloWorld', 'HelloWorld.cpp'), 'r').read(),
- [open(path_from_root('tests', 'bullet', 'output.txt'), 'r').read(), # different roundings
- open(path_from_root('tests', 'bullet', 'output2.txt'), 'r').read(),
- open(path_from_root('tests', 'bullet', 'output3.txt'), 'r').read()],
- libraries=self.get_library('bullet', [os.path.join('src', '.libs', 'libBulletDynamics.a'),
- os.path.join('src', '.libs', 'libBulletCollision.a'),
- os.path.join('src', '.libs', 'libLinearMath.a')],
- configure_args=['--disable-demos','--disable-dependency-tracking']),
- includes=[path_from_root('tests', 'bullet', 'src')])
+ def test():
+ self.do_run(open(path_from_root('tests', 'bullet', 'Demos', 'HelloWorld', 'HelloWorld.cpp'), 'r').read(),
+ [open(path_from_root('tests', 'bullet', 'output.txt'), 'r').read(), # different roundings
+ open(path_from_root('tests', 'bullet', 'output2.txt'), 'r').read(),
+ open(path_from_root('tests', 'bullet', 'output3.txt'), 'r').read()],
+ libraries=self.get_library('bullet', [os.path.join('src', '.libs', 'libBulletDynamics.a'),
+ os.path.join('src', '.libs', 'libBulletCollision.a'),
+ os.path.join('src', '.libs', 'libLinearMath.a')],
+ configure_args=['--disable-demos','--disable-dependency-tracking']),
+ includes=[path_from_root('tests', 'bullet', 'src')])
+ test()
+
+ assert 'asm2g' in test_modes
+ if self.run_name == 'asm2g':
+ # Test forced alignment
+ print >> sys.stderr, 'testing FORCE_ALIGNED_MEMORY'
+ old = open('src.cpp.o.js').read()
+ Settings.FORCE_ALIGNED_MEMORY = 1
+ test()
+ new = open('src.cpp.o.js').read()
+ print len(old), len(new), old.count('tempBigInt'), new.count('tempBigInt')
+ assert len(old) > len(new)
+ assert old.count('tempBigInt') > new.count('tempBigInt')
def test_poppler(self):
if self.emcc_args is None: return self.skip('very slow, we only do this in emcc runs')
@@ -9269,6 +9320,7 @@ finalizing 3 (global == 0)
def make_run(fullname, name=-1, compiler=-1, llvm_opts=0, embetter=0, quantum_size=0, typed_arrays=0, emcc_args=None, env='{}'):
exec('''
class %s(T):
+ run_name = '%s'
env = %s
def tearDown(self):
@@ -9333,7 +9385,7 @@ class %s(T):
Building.pick_llvm_opts(3)
TT = %s
-''' % (fullname, env, fullname, fullname, compiler, str(emcc_args), llvm_opts, embetter, quantum_size, typed_arrays, fullname))
+''' % (fullname, fullname, env, fullname, fullname, compiler, str(emcc_args), llvm_opts, embetter, quantum_size, typed_arrays, fullname))
return TT
# Make one run with the defaults
@@ -12529,7 +12581,16 @@ elif 'benchmark' in str(sys.argv):
print ' JavaScript: mean: %.3f (+-%.3f) secs median: %.3f range: %.3f-%.3f (noise: %3.3f%%) (%d runs)' % (mean, std, median, min(times), max(times), 100*std/mean, reps)
print ' Native : mean: %.3f (+-%.3f) secs median: %.3f range: %.3f-%.3f (noise: %3.3f%%) JS is %.2f X slower' % (mean_native, std_native, median_native, min(native_times), max(native_times), 100*std_native/mean_native, final)
- def do_benchmark(self, name, src, args=[], expected_output='FAIL', emcc_args=[], native_args=[], shared_args=[], force_c=False, reps=TEST_REPS):
+ def do_benchmark(self, name, src, expected_output='FAIL', args=[], emcc_args=[], native_args=[], shared_args=[], force_c=False, reps=TEST_REPS):
+ # standard arguments for timing:
+ # 0: no runtime, just startup
+ # 1: very little runtime
+ # 2: 0.5 seconds
+ # 3: 1 second
+ # 4: 5 seconds
+ # 5: 10 seconds
+ args = args or ['3']
+
dirname = self.get_dir()
filename = os.path.join(dirname, name + '.c' + ('' if force_c else 'pp'))
f = open(filename, 'w')
@@ -12553,7 +12614,8 @@ elif 'benchmark' in str(sys.argv):
for i in range(reps):
start = time.time()
js_output = run_js(final_filename, engine=JS_ENGINE, args=args, stderr=PIPE, full_output=True)
- if i == 0 and 'Successfully compiled asm.js code' in js_output:
+
+ if i == 0 and 'uccessfully compiled asm.js code' in js_output:
if 'asm.js link error' not in js_output:
print "[%s was asm.js'ified]" % name
curr = time.time()-start
@@ -12618,7 +12680,7 @@ elif 'benchmark' in str(sys.argv):
return 0;
}
'''
- self.do_benchmark('primes', src, [], 'lastprime: 3043739.')
+ self.do_benchmark('primes', src, 'lastprime: 3043739.')
def test_memops(self):
src = '''
@@ -12651,7 +12713,7 @@ elif 'benchmark' in str(sys.argv):
return 0;
}
'''
- self.do_benchmark('memops', src, [], 'final: 400.')
+ self.do_benchmark('memops', src, 'final: 400.')
def zzztest_files(self):
src = r'''
@@ -12694,7 +12756,7 @@ elif 'benchmark' in str(sys.argv):
return 0;
}
'''
- self.do_benchmark(src, [], 'ok')
+ self.do_benchmark(src, 'ok')
def test_copy(self):
src = r'''
@@ -12748,7 +12810,7 @@ elif 'benchmark' in str(sys.argv):
return 0;
}
'''
- self.do_benchmark('copy', src, [], 'sum:2836\n')
+ self.do_benchmark('copy', src, 'sum:2836\n')
def test_fannkuch(self):
src = open(path_from_root('tests', 'fannkuch.cpp'), 'r').read().replace(
@@ -12768,7 +12830,7 @@ elif 'benchmark' in str(sys.argv):
'''
)
assert 'switch(arg)' in src
- self.do_benchmark('fannkuch', src, [], 'Pfannkuchen(11) = 51.')
+ self.do_benchmark('fannkuch', src, 'Pfannkuchen(11) = 51.')
def test_corrections(self):
src = r'''
@@ -12801,7 +12863,7 @@ elif 'benchmark' in str(sys.argv):
return 0;
}
'''
- self.do_benchmark('corrections', src, [], 'final: 40006013:10225.', emcc_args=['-s', 'CORRECT_SIGNS=1', '-s', 'CORRECT_OVERFLOWS=1', '-s', 'CORRECT_ROUNDINGS=1'])
+ self.do_benchmark('corrections', src, 'final: 40006013:10225.', emcc_args=['-s', 'CORRECT_SIGNS=1', '-s', 'CORRECT_OVERFLOWS=1', '-s', 'CORRECT_ROUNDINGS=1'])
def fasta(self, name, double_rep, emcc_args=[]):
src = open(path_from_root('tests', 'fasta.cpp'), 'r').read().replace('double', double_rep)
@@ -12819,7 +12881,7 @@ elif 'benchmark' in str(sys.argv):
}
''')
assert 'switch(arg)' in src
- self.do_benchmark('fasta', src, [], '''GGCCGGGCGCGGTGGCTCACGCCTGTAATCCCAGCACTTTGGGAGGCCGAGGCGGGCGGA\nTCACCTGAGGTCAGGAGTTCGAGACCAGCCTGGCCAACATGGTGAAACCCCGTCTCTACT\nAAAAATACAAAAATTAGCCGGGCGTGGTGGCGCGCGCCTGTAATCCCAGCTACTCGGGAG\nGCTGAGGCAGGAGAATCGCTTGAACCCGGGAGGCGGAGGTTGCAGTGAGCCGAGATCGCG\nCCACTGCACTCCAGCCTGGGCGACAGAGCGAGACTCCGTCTCAAAAAGGCCGGGCGCGGT\nGGCTCACGCCTGTAATCCCAGCACTTTGGGAGGCCGAGGCGGGCGGATCACCTGAGGTCA\nGGAGTTCGAGACCAGCCTGGCCAACATGGTGAAACCCCGTCTCTACTAAAAATACAAAAA\nTTAGCCGGGCGTGGTGGCGCGCGCCTGTAATCCCAGCTACTCGGGAGGCTGAGGCAGGAG\nAATCGCTTGAACCCGGGAGGCGGAGGTTGCAGTGAGCCGAGATCGCGCCACTGCACTCCA\nGCCTGGGCGA''')
+ self.do_benchmark('fasta', src, '''GGCCGGGCGCGGTGGCTCACGCCTGTAATCCCAGCACTTTGGGAGGCCGAGGCGGGCGGA\nTCACCTGAGGTCAGGAGTTCGAGACCAGCCTGGCCAACATGGTGAAACCCCGTCTCTACT\nAAAAATACAAAAATTAGCCGGGCGTGGTGGCGCGCGCCTGTAATCCCAGCTACTCGGGAG\nGCTGAGGCAGGAGAATCGCTTGAACCCGGGAGGCGGAGGTTGCAGTGAGCCGAGATCGCG\nCCACTGCACTCCAGCCTGGGCGACAGAGCGAGACTCCGTCTCAAAAAGGCCGGGCGCGGT\nGGCTCACGCCTGTAATCCCAGCACTTTGGGAGGCCGAGGCGGGCGGATCACCTGAGGTCA\nGGAGTTCGAGACCAGCCTGGCCAACATGGTGAAACCCCGTCTCTACTAAAAATACAAAAA\nTTAGCCGGGCGTGGTGGCGCGCGCCTGTAATCCCAGCTACTCGGGAGGCTGAGGCAGGAG\nAATCGCTTGAACCCGGGAGGCGGAGGTTGCAGTGAGCCGAGATCGCGCCACTGCACTCCA\nGCCTGGGCGA''')
def test_fasta_float(self):
self.fasta('fasta_float', 'float')
@@ -12832,11 +12894,11 @@ elif 'benchmark' in str(sys.argv):
def test_skinning(self):
src = open(path_from_root('tests', 'skinning_test_no_simd.cpp'), 'r').read()
- self.do_benchmark('skinning', src, [], 'blah=0.000000')
+ self.do_benchmark('skinning', src, 'blah=0.000000')
def test_life(self):
src = open(path_from_root('tests', 'life.c'), 'r').read()
- self.do_benchmark('life', src, [], '''--------------------------------
+ self.do_benchmark('life', src, '''--------------------------------
[][] [] []
[][] [][] [] []
[][] [] []
@@ -12874,7 +12936,7 @@ elif 'benchmark' in str(sys.argv):
def test_nbody_java(self): # tests xmlvm compiled java, including bitcasts of doubles, i64 math, etc.
args = [path_from_root('tests', 'nbody-java', x) for x in os.listdir(path_from_root('tests', 'nbody-java')) if x.endswith('.c')] + \
['-I' + path_from_root('tests', 'nbody-java')]
- self.do_benchmark('nbody_java', '', ['11500000'], '''Time(s)''',
+ self.do_benchmark('nbody_java', '', '''Time(s)''',
force_c=True, emcc_args=args + ['-s', 'PRECISE_I64_MATH=1', '--llvm-lto', '0'], native_args=args + ['-lgc', '-std=c99', '-target', 'x86_64-pc-linux-gnu', '-lm'])
def test_zlib(self):
@@ -12883,7 +12945,7 @@ elif 'benchmark' in str(sys.argv):
['-I' + path_from_root('tests', 'zlib')]
native_args = self.get_library('zlib_native', os.path.join('libz.a'), make_args=['libz.a'], native=True) + \
['-I' + path_from_root('tests', 'zlib')]
- self.do_benchmark('zlib', src, [], '''sizes: 100000,25906
+ self.do_benchmark('zlib', src, '''sizes: 100000,25906
ok.
''',
force_c=True, emcc_args=emcc_args, native_args=native_args)
@@ -12897,7 +12959,7 @@ ok.
emcc_args = js_lib + ['-I' + path_from_root('tests', 'box2d')]
native_args = native_lib + ['-I' + path_from_root('tests', 'box2d')]
- self.do_benchmark('box2d', src, [], 'frame averages', emcc_args=emcc_args, native_args=native_args)
+ self.do_benchmark('box2d', src, 'frame averages', emcc_args=emcc_args, native_args=native_args)
def test_zzz_bullet(self): # Called thus so it runs late in the alphabetical cycle... it is long
src = open(path_from_root('tests', 'bullet', 'Demos', 'Benchmarks', 'BenchmarkDemo.cpp'), 'r').read() + \
@@ -12919,7 +12981,7 @@ ok.
native_args = native_lib + ['-I' + path_from_root('tests', 'bullet', 'src'),
'-I' + path_from_root('tests', 'bullet', 'Demos', 'Benchmarks')]
- self.do_benchmark('bullet', src, [], '\nok.\n', emcc_args=emcc_args, native_args=native_args)
+ self.do_benchmark('bullet', src, '\nok.\n', emcc_args=emcc_args, native_args=native_args)
elif 'sanity' in str(sys.argv):
@@ -13423,8 +13485,17 @@ if __name__ == '__main__':
arg = sys.argv[i]
if arg.startswith('skip:'):
which = arg.split('skip:')[1]
- print >> sys.stderr, 'will skip "%s"' % which
- exec(which + ' = RunnerCore.skipme')
+ if which.startswith('ALL.'):
+ ignore, test = which.split('.')
+ which = map(lambda mode: mode+'.'+test, test_modes)
+ else:
+ which = [which]
+
+ print >> sys.stderr, ','.join(which)
+ for test in which:
+ print >> sys.stderr, 'will skip "%s"' % test
+ exec(test + ' = RunnerCore.skipme')
+
sys.argv[i] = ''
sys.argv = filter(lambda arg: arg, sys.argv)
diff --git a/tools/eliminator/asm-eliminator-test-output.js b/tools/eliminator/asm-eliminator-test-output.js
index b519cdf9..8da7a5bc 100644
--- a/tools/eliminator/asm-eliminator-test-output.js
+++ b/tools/eliminator/asm-eliminator-test-output.js
@@ -66,11 +66,9 @@ function __ZN5identC2EiPKcPci($this, $n, $a) {
}
function _vec2Length($this) {
$this = $this | 0;
- var $__first_addr_i = 0, $__last_addr_i = 0, __stackBase__ = 0;
+ var __stackBase__ = 0;
__stackBase__ = STACKTOP;
STACKTOP = STACKTOP + 8 | 0;
- $__first_addr_i = __stackBase__;
- $__last_addr_i = __stackBase__ + 4;
STACKTOP = __stackBase__;
return 0;
}
@@ -109,18 +107,22 @@ function label() {
}
}
function switchy() {
- var no = 0, yes = 0;
+ var no = 0, yes = 0, a = 0, b = 0;
while (1) switch (label | 0) {
- case x:
+ case 1:
no = 100;
break;
- case y:
+ case 2:
yes = 111;
yes = yes * 2;
print(yes);
yes--;
print(yes / 2);
continue;
+ case 3:
+ a = 5;
+ b = a;
+ break;
}
}
function confuusion() {
@@ -133,4 +135,233 @@ function tempDouble(a) {
a = +a;
f(a * a);
}
+function _org_apache_harmony_luni_util_NumberConverter_freeFormat__($me) {
+ $me = $me | 0;
+ var $_r2_sroa_0 = 0, $_r3_sroa_0 = 0, $$etemp$1 = 0, $6 = 0, $7 = 0, $10 = 0, $11 = +0, $15 = 0, $_r2_sroa_0_0_cast283 = 0, $_r3_sroa_0_0_cast247 = 0, $_r3_sroa_0_0_load244 = +0, $_r3_sroa_0_0_load244$$SHADOW$0 = 0, $_r2_sroa_0_0_load = +0, $_r2_sroa_0_0_load$$SHADOW$0 = 0, $trunc297 = 0, $25 = 0, $26 = 0, $smax = 0, $28 = 0, $_r3_sroa_0_0_load239 = +0, $_pre_phi301 = 0, $_r3_sroa_0_0_cast264_pre_phi = 0, $_r2_sroa_0_0_load265 = +0, $33 = 0, $34 = 0, $_r3_sroa_0_0_cast253 = 0, $36 = 0, $37 = 0, $_r3_sroa_0_0_load243 = +0, $_r2_sroa_0_0_cast = 0, $45 = 0, $_sink_in = +0, $_r3_sroa_0_0_load241 = +0, $_r2_sroa_0_0_load266287 = 0, $_r1_sroa_0_0 = +0, $47 = 0, $48$0 = 0, $48$1 = 0, $_r1_sroa_0_0_extract_trunc185 = 0, $_r1_sroa_0_1_in$0 = 0, $_r1_sroa_0_1_in$1 = 0, $_r1_sroa_0_0_extract_trunc169 = 0, $_r1_sroa_0_2 = +0, $64 = 0, $65 = 0, $69 = 0, $76 = 0, $82 = 0, $_r1_sroa_0_0_extract_trunc = 0, $$etemp$15 = 0, $105 = 0, $106 = 0, $107 = 0, $108 = 0, $109 = 0, $110 = 0, $112 = 0, $113 = 0, $118 = 0, $_r3_sroa_0_0_load242 = +0, label = 0, __stackBase__ = 0;
+ __stackBase__ = STACKTOP;
+ STACKTOP = STACKTOP + 16 | 0;
+ $_r2_sroa_0 = __stackBase__ | 0;
+ $_r3_sroa_0 = __stackBase__ + 8 | 0;
+ if ((HEAP32[(114668 | 0) >> 2] | 0 | 0) == 0) {
+ HEAP32[(114664 | 0) >> 2] = 1;
+ HEAP32[(114668 | 0) >> 2] = 1;
+ $$etemp$1 = 114672 | 0;
+ HEAP32[($$etemp$1 | 0) >> 2] = -1;
+ HEAP32[($$etemp$1 + 4 | 0) >> 2] = -1;
+ HEAP32[(114684 | 0) >> 2] = 25296 | 0;
+ HEAP32[(114704 | 0) >> 2] = 110728;
+ HEAP32[(114712 | 0) >> 2] = 8;
+ HEAP32[(114784 | 0 | 0) >> 2] = HEAP32[(107856 | 0 | 0) >> 2] | 0;
+ HEAP32[(114784 | 0 | 0) + 4 >> 2] = HEAP32[(107856 | 0 | 0) + 4 >> 2] | 0;
+ HEAP32[(114784 | 0 | 0) + 8 >> 2] = HEAP32[(107856 | 0 | 0) + 8 >> 2] | 0;
+ HEAP32[(114784 | 0 | 0) + 12 >> 2] = HEAP32[(107856 | 0 | 0) + 12 >> 2] | 0;
+ HEAP32[(114784 | 0 | 0) + 16 >> 2] = HEAP32[(107856 | 0 | 0) + 16 >> 2] | 0;
+ HEAP32[(114784 | 0 | 0) + 20 >> 2] = HEAP32[(107856 | 0 | 0) + 20 >> 2] | 0;
+ }
+ $6 = _org_xmlvm_runtime_XMLVMArray_createSingleDimension___java_lang_Class_int(HEAP32[138960 >> 2] | 0, 25) | 0;
+ $7 = $me + 8 | 0;
+ $10 = HEAP32[($me + 20 | 0) >> 2] | 0;
+ $11 = (HEAP32[tempDoublePtr >> 2] = $10, HEAP32[tempDoublePtr + 4 >> 2] = 0, +HEAPF64[tempDoublePtr >> 3]);
+ if (($10 | 0) > -1) {
+ HEAP32[$_r2_sroa_0 >> 2] = 0;
+ $_r2_sroa_0_0_load265 = +HEAPF64[$_r2_sroa_0 >> 3];
+ $_r3_sroa_0_0_cast264_pre_phi = $_r3_sroa_0;
+ $_pre_phi301 = $6 + 16 | 0;
+ } else {
+ $15 = $6 + 16 | 0;
+ HEAP16[(HEAP32[$15 >> 2] | 0) >> 1] = 48;
+ $_r2_sroa_0_0_cast283 = $_r2_sroa_0;
+ HEAP16[((HEAP32[$15 >> 2] | 0) + 2 | 0) >> 1] = 46;
+ HEAP32[$_r2_sroa_0_0_cast283 >> 2] = 2;
+ $_r3_sroa_0_0_cast247 = $_r3_sroa_0;
+ HEAP32[$_r3_sroa_0_0_cast247 >> 2] = $10 + 1 | 0;
+ $_r3_sroa_0_0_load244 = +HEAPF64[$_r3_sroa_0 >> 3];
+ $_r3_sroa_0_0_load244$$SHADOW$0 = HEAP32[($_r3_sroa_0 | 0) >> 2] | 0;
+ $_r2_sroa_0_0_load = +HEAPF64[$_r2_sroa_0 >> 3];
+ $_r2_sroa_0_0_load$$SHADOW$0 = HEAP32[($_r2_sroa_0 | 0) >> 2] | 0;
+ HEAPF64[$_r3_sroa_0 >> 3] = $_r2_sroa_0_0_load;
+ HEAPF64[$_r2_sroa_0 >> 3] = $_r3_sroa_0_0_load244;
+ $trunc297 = $_r3_sroa_0_0_load244$$SHADOW$0;
+ $25 = $_r2_sroa_0_0_load$$SHADOW$0;
+ if (($trunc297 | 0) < 0) {
+ $26 = $trunc297 + 1 | 0;
+ $smax = ($26 | 0) > 0 ? $26 : 0;
+ $28 = $25 + $smax | 0;
+ $113 = $25;
+ $112 = $trunc297;
+ while (1) {
+ HEAP16[((HEAP32[$15 >> 2] | 0) + ($113 << 1) | 0) >> 1] = 48;
+ $118 = $112 + 1 | 0;
+ if (($118 | 0) < 0) {
+ $113 = $113 + 1 | 0;
+ $112 = $118;
+ } else {
+ break;
+ }
+ }
+ HEAP32[$_r3_sroa_0_0_cast247 >> 2] = $28 - $trunc297 | 0;
+ HEAP32[$_r2_sroa_0_0_cast283 >> 2] = $smax;
+ $_r3_sroa_0_0_load239 = +HEAPF64[$_r3_sroa_0 >> 3];
+ } else {
+ $_r3_sroa_0_0_load239 = $_r2_sroa_0_0_load;
+ }
+ HEAPF64[$_r2_sroa_0 >> 3] = $_r3_sroa_0_0_load239;
+ $_r2_sroa_0_0_load265 = $_r3_sroa_0_0_load239;
+ $_r3_sroa_0_0_cast264_pre_phi = $_r3_sroa_0_0_cast247;
+ $_pre_phi301 = $15;
+ }
+ $33 = $me + 16 | 0;
+ $34 = HEAP32[$33 >> 2] | 0;
+ $_r3_sroa_0_0_cast253 = $_r3_sroa_0;
+ HEAP32[$_r3_sroa_0_0_cast253 >> 2] = $34;
+ $36 = $me + 12 | 0;
+ $37 = HEAP32[$36 >> 2] | 0;
+ HEAP32[$36 >> 2] = $37 + 1 | 0;
+ HEAP32[$_r3_sroa_0_0_cast264_pre_phi >> 2] = HEAP32[((HEAP32[($34 + 16 | 0) >> 2] | 0) + ($37 << 2) | 0) >> 2] | 0;
+ $_r3_sroa_0_0_load243 = +HEAPF64[$_r3_sroa_0 >> 3];
+ HEAPF64[$_r3_sroa_0 >> 3] = $_r2_sroa_0_0_load265;
+ HEAPF64[$_r2_sroa_0 >> 3] = $11;
+ $_r2_sroa_0_0_cast = $_r2_sroa_0;
+ $45 = $7;
+ $_r1_sroa_0_0 = $_r3_sroa_0_0_load243;
+ $_r2_sroa_0_0_load266287 = $10;
+ $_r3_sroa_0_0_load241 = $_r2_sroa_0_0_load265;
+ $_sink_in = $_r2_sroa_0_0_load265;
+ while (1) {
+ HEAPF64[tempDoublePtr >> 3] = $_sink_in;
+ $47 = HEAP32[tempDoublePtr >> 2] | 0;
+ HEAPF64[tempDoublePtr >> 3] = $_r1_sroa_0_0;
+ $48$0 = HEAP32[tempDoublePtr >> 2] | 0;
+ $48$1 = HEAP32[tempDoublePtr + 4 >> 2] | 0;
+ $_r1_sroa_0_0_extract_trunc185 = $48$0;
+ do {
+ if (($_r1_sroa_0_0_extract_trunc185 | 0) == -1) {
+ if (($_r2_sroa_0_0_load266287 | 0) < -1) {
+ $_r1_sroa_0_2 = $_r3_sroa_0_0_load241;
+ break;
+ }
+ HEAP16[((HEAP32[$_pre_phi301 >> 2] | 0) + ($47 << 1) | 0) >> 1] = 48;
+ $_r1_sroa_0_1_in$1 = 0 | $48$1 & -1;
+ $_r1_sroa_0_1_in$0 = $47 + 1 | 0 | $48$0 & 0;
+ label = 785;
+ break;
+ } else {
+ HEAP16[((HEAP32[$_pre_phi301 >> 2] | 0) + ($47 << 1) | 0) >> 1] = ($_r1_sroa_0_0_extract_trunc185 + 48 | 0) & 65535;
+ $_r1_sroa_0_1_in$1 = 0;
+ $_r1_sroa_0_1_in$0 = $47 + 1 | 0;
+ label = 785;
+ break;
+ }
+ } while (0);
+ do {
+ if ((label | 0) == 785) {
+ label = 0;
+ if (!(($_r2_sroa_0_0_load266287 | 0) == 0)) {
+ $_r1_sroa_0_2 = (HEAP32[tempDoublePtr >> 2] = $_r1_sroa_0_1_in$0, HEAP32[tempDoublePtr + 4 >> 2] = $_r1_sroa_0_1_in$1, +HEAPF64[tempDoublePtr >> 3]);
+ break;
+ }
+ $_r1_sroa_0_0_extract_trunc169 = $_r1_sroa_0_1_in$0;
+ HEAP32[$_r3_sroa_0_0_cast264_pre_phi >> 2] = $_r1_sroa_0_0_extract_trunc169 + 1 | 0;
+ HEAP16[((HEAP32[$_pre_phi301 >> 2] | 0) + ($_r1_sroa_0_0_extract_trunc169 << 1) | 0) >> 1] = 46;
+ $_r1_sroa_0_2 = +HEAPF64[$_r3_sroa_0 >> 3];
+ }
+ } while (0);
+ $64 = $_r2_sroa_0_0_load266287 - 1 | 0;
+ $65 = HEAP32[$36 >> 2] | 0;
+ HEAP32[$_r3_sroa_0_0_cast264_pre_phi >> 2] = $65;
+ if (($65 | 0) < (HEAP32[$45 >> 2] | 0 | 0)) {
+ $69 = HEAP32[$33 >> 2] | 0;
+ HEAP32[$_r3_sroa_0_0_cast253 >> 2] = $69;
+ HEAP32[$36 >> 2] = $65 + 1 | 0;
+ $76 = HEAP32[((HEAP32[($69 + 16 | 0) >> 2] | 0) + ($65 << 2) | 0) >> 2] | 0;
+ HEAP32[$_r3_sroa_0_0_cast264_pre_phi >> 2] = $76;
+ if (!(($76 | 0) != -1 | ($64 | 0) > -2)) {
+ break;
+ }
+ } else {
+ HEAP32[$_r3_sroa_0_0_cast264_pre_phi >> 2] = -1;
+ if (!(($64 | 0) > -2)) {
+ break;
+ }
+ }
+ $_r3_sroa_0_0_load242 = +HEAPF64[$_r3_sroa_0 >> 3];
+ HEAPF64[$_r3_sroa_0 >> 3] = $_r1_sroa_0_2;
+ $_r1_sroa_0_0 = $_r3_sroa_0_0_load242;
+ $_r2_sroa_0_0_load266287 = $64;
+ $_r3_sroa_0_0_load241 = $_r1_sroa_0_2;
+ $_sink_in = $_r1_sroa_0_2;
+ }
+ HEAP32[$_r2_sroa_0_0_cast >> 2] = $64;
+ if ((HEAP32[(106148 | 0) >> 2] | 0 | 0) == 0) {
+ ___INIT_java_lang_String();
+ }
+ $82 = _GC_MALLOC(36 | 0) | 0;
+ HEAP32[$82 >> 2] = 106144;
+ _memset($82 + 4 | 0 | 0 | 0, 0 | 0 | 0, 32 | 0 | 0);
+ HEAP32[$_r2_sroa_0 >> 2] = $82;
+ HEAPF64[tempDoublePtr >> 3] = $_r1_sroa_0_2;
+ $_r1_sroa_0_0_extract_trunc = HEAP32[tempDoublePtr >> 2] | 0;
+ HEAP32[($82 + 8 | 0) >> 2] = 0;
+ HEAP32[($82 + 12 | 0) >> 2] = 0;
+ HEAP32[($82 + 16 | 0) >> 2] = 0;
+ if (($_r1_sroa_0_0_extract_trunc | 0) < 0) {
+ _XMLVM_ERROR(16136 | 0, 13208 | 0, 132112 | 0, 830);
+ return 0 | 0;
+ }
+ if ((HEAP32[($6 + 12 | 0) >> 2] | 0 | 0) < ($_r1_sroa_0_0_extract_trunc | 0)) {
+ _XMLVM_ERROR(16136 | 0, 13208 | 0, 132112 | 0, 830);
+ return 0 | 0;
+ }
+ HEAP32[($82 + 24 | 0) >> 2] = 0;
+ if (!((HEAP32[(114668 | 0) >> 2] | 0 | 0) == 0)) {
+ $105 = HEAP32[138960 >> 2] | 0;
+ $106 = _org_xmlvm_runtime_XMLVMArray_createSingleDimension___java_lang_Class_int($105, $_r1_sroa_0_0_extract_trunc) | 0;
+ $107 = $82 + 20 | 0;
+ $108 = $107;
+ HEAP32[$108 >> 2] = $106;
+ $109 = $82 + 28 | 0;
+ $110 = $109;
+ HEAP32[$110 >> 2] = $_r1_sroa_0_0_extract_trunc;
+ _java_lang_System_arraycopy___java_lang_Object_int_java_lang_Object_int_int($6, 0, $106, 0, $_r1_sroa_0_0_extract_trunc);
+ STACKTOP = __stackBase__;
+ return $82 | 0;
+ }
+ HEAP32[(114664 | 0) >> 2] = 1;
+ HEAP32[(114668 | 0) >> 2] = 1;
+ $$etemp$15 = 114672 | 0;
+ HEAP32[($$etemp$15 | 0) >> 2] = -1;
+ HEAP32[($$etemp$15 + 4 | 0) >> 2] = -1;
+ HEAP32[(114684 | 0) >> 2] = 25296 | 0;
+ HEAP32[(114704 | 0) >> 2] = 110728;
+ HEAP32[(114712 | 0) >> 2] = 8;
+ HEAP32[(114784 | 0 | 0) >> 2] = HEAP32[(107856 | 0 | 0) >> 2] | 0;
+ HEAP32[(114784 | 0 | 0) + 4 >> 2] = HEAP32[(107856 | 0 | 0) + 4 >> 2] | 0;
+ HEAP32[(114784 | 0 | 0) + 8 >> 2] = HEAP32[(107856 | 0 | 0) + 8 >> 2] | 0;
+ HEAP32[(114784 | 0 | 0) + 12 >> 2] = HEAP32[(107856 | 0 | 0) + 12 >> 2] | 0;
+ HEAP32[(114784 | 0 | 0) + 16 >> 2] = HEAP32[(107856 | 0 | 0) + 16 >> 2] | 0;
+ HEAP32[(114784 | 0 | 0) + 20 >> 2] = HEAP32[(107856 | 0 | 0) + 20 >> 2] | 0;
+ $105 = HEAP32[138960 >> 2] | 0;
+ $106 = _org_xmlvm_runtime_XMLVMArray_createSingleDimension___java_lang_Class_int($105, $_r1_sroa_0_0_extract_trunc) | 0;
+ $107 = $82 + 20 | 0;
+ $108 = $107;
+ HEAP32[$108 >> 2] = $106;
+ $109 = $82 + 28 | 0;
+ $110 = $109;
+ HEAP32[$110 >> 2] = $_r1_sroa_0_0_extract_trunc;
+ _java_lang_System_arraycopy___java_lang_Object_int_java_lang_Object_int_int($6, 0, $106, 0, $_r1_sroa_0_0_extract_trunc);
+ STACKTOP = __stackBase__;
+ return $82 | 0;
+}
+function __ZN23b2EdgeAndPolygonContact8EvaluateEP10b2ManifoldRK11b2TransformS4_($this, $manifold, $xfA, $xfB) {
+ $this = $this | 0;
+ $manifold = $manifold | 0;
+ $xfA = $xfA | 0;
+ $xfB = $xfB | 0;
+ var __stackBase__ = 0;
+ __stackBase__ = STACKTOP;
+ STACKTOP = STACKTOP + 256 | 0;
+ __ZN12b2EPCollider7CollideEP10b2ManifoldPK11b2EdgeShapeRK11b2TransformPK14b2PolygonShapeS7_(__stackBase__ | 0, $manifold, HEAP32[((HEAP32[($this + 48 | 0) >> 2] | 0) + 12 | 0) >> 2] | 0, $xfA, HEAP32[((HEAP32[($this + 52 | 0) >> 2] | 0) + 12 | 0) >> 2] | 0, $xfB);
+ STACKTOP = __stackBase__;
+ return;
+}
diff --git a/tools/eliminator/asm-eliminator-test.js b/tools/eliminator/asm-eliminator-test.js
index ff67af47..5f75e9c1 100644
--- a/tools/eliminator/asm-eliminator-test.js
+++ b/tools/eliminator/asm-eliminator-test.js
@@ -143,17 +143,22 @@ function label() {
}
function switchy() {
var no = 0, yes = 0;
+ var a = 0, b = 0;
while (1) switch (label | 0) {
- case x:
+ case 1:
no = 100; // eliminatable in theory, but eliminator does not look into switch. must leave def above as well.
break;
- case y:
+ case 2:
yes = 111;
yes = yes*2;
print(yes);
yes--;
print(yes/2);
continue;
+ case 3:
+ a = 5;
+ b = a;
+ break;
}
}
function confuusion() {
@@ -170,5 +175,423 @@ function tempDouble(a) {
y = a*a;
f(y);
}
-// EMSCRIPTEN_GENERATED_FUNCTIONS: ["asm", "__Z11printResultPiS_j", "_segment_holding", "__ZN5identC2EiPKcPci", "_vec2Length", "exc", "label", "confuusion", "tempDouble"]
+function _org_apache_harmony_luni_util_NumberConverter_freeFormat__($me) {
+ $me = $me | 0;
+ var $_r2_sroa_0 = 0, $_r3_sroa_0 = 0, $1 = 0, $2 = 0, $$etemp$1 = 0, $$etemp$0$0 = 0, $$etemp$0$1 = 0, $st$2$0 = 0;
+ var $st$3$1 = 0, $5 = 0, $6 = 0, $7 = 0, $8 = 0, $9 = 0, $10 = 0, $_r1_sroa_0_0_insert_ext191$0 = 0;
+ var $_r1_sroa_0_0_insert_ext191$1 = 0, $11 = +0, $12 = 0, $14 = 0, $15 = 0, $16 = 0, $17 = 0, $_r2_sroa_0_0_cast283 = 0;
+ var $18 = 0, $19 = 0, $20 = 0, $21 = 0, $_r3_sroa_0_0_cast247 = 0, $_r3_sroa_0_0_load244 = +0, $ld$4$0 = 0, $_r3_sroa_0_0_load244$$SHADOW$0 = 0;
+ var $ld$5$1 = 0, $_r3_sroa_0_0_load244$$SHADOW$1 = 0, $_r2_sroa_0_0_load = +0, $ld$6$0 = 0, $_r2_sroa_0_0_load$$SHADOW$0 = 0, $ld$7$1 = 0, $_r2_sroa_0_0_load$$SHADOW$1 = 0, $22$0 = 0;
+ var $22$1 = 0, $trunc297$0 = 0, $trunc297 = 0, $23 = 0, $24$0 = 0, $24$1 = 0, $25$0 = 0, $25 = 0;
+ var $26 = 0, $27 = 0, $smax = 0, $28 = 0, $29 = 0, $_r3_sroa_0_0_load239_pre = +0, $ld$8$0 = 0, $_r3_sroa_0_0_load239_pre$$SHADOW$0 = 0;
+ var $ld$9$1 = 0, $_r3_sroa_0_0_load239_pre$$SHADOW$1 = 0, $_r3_sroa_0_0_load239 = +0, $_pre_phi301 = 0, $_r3_sroa_0_0_cast264_pre_phi = 0, $_r2_sroa_0_0_load265 = +0, $32 = 0, $33 = 0;
+ var $34 = 0, $_r3_sroa_0_0_cast253 = 0, $35 = 0, $36 = 0, $37 = 0, $38 = 0, $39 = 0, $40 = 0;
+ var $41 = 0, $42 = 0, $43 = 0, $44 = 0, $_r3_sroa_0_0_load243 = +0, $ld$10$0 = 0, $_r3_sroa_0_0_load243$$SHADOW$0 = 0, $ld$11$1 = 0;
+ var $_r3_sroa_0_0_load243$$SHADOW$1 = 0, $_r2_sroa_0_0_cast = 0, $45 = 0, $_sink_in = +0, $_r3_sroa_0_0_load241 = +0, $_r2_sroa_0_0_load266287 = 0, $_r1_sroa_0_0 = +0, $_sink$0 = 0, $_sink$1 = 0;
+ var $47$0 = 0, $47 = 0, $48$0 = 0, $48$1 = 0, $_r1_sroa_0_0_extract_trunc185$0 = 0, $_r1_sroa_0_0_extract_trunc185 = 0, $49 = 0, $51 = 0, $52 = 0;
+ var $53 = 0, $54 = 0, $55 = 0, $56 = 0, $_r1_sroa_0_0_insert_ext195$0 = 0, $_r1_sroa_0_0_insert_ext195$1 = 0, $_r1_sroa_0_1_in$0 = 0, $_r1_sroa_0_1_in$1 = 0;
+ var $_r1_sroa_0_1 = +0, $58 = 0, $_r1_sroa_0_0_extract_trunc169$0 = 0, $_r1_sroa_0_0_extract_trunc169 = 0, $60 = 0, $61 = 0, $62 = 0, $63 = 0;
+ var $_r3_sroa_0_0_load240 = +0, $ld$12$0 = 0, $_r3_sroa_0_0_load240$$SHADOW$0 = 0, $ld$13$1 = 0, $_r3_sroa_0_0_load240$$SHADOW$1 = 0, $_r1_sroa_0_2 = +0, $64 = 0, $65 = 0;
+ var $66 = 0, $67 = 0, $69 = 0, $70 = 0, $71 = 0, $72 = 0, $73 = 0, $74 = 0;
+ var $75 = 0, $76 = 0, $phitmp = 0, $77 = 0, $or_cond = 0, $79 = 0, $80 = 0, $82 = 0;
+ var $83 = 0, $84 = 0, $_r2_sroa_0_0_cast269 = 0, $85$0 = 0, $85$1 = 0, $_r1_sroa_0_0_extract_trunc$0 = 0, $_r1_sroa_0_0_extract_trunc = 0, $86 = 0, $87 = 0;
+ var $88 = 0, $89 = 0, $90 = 0, $91 = 0, $92 = 0, $94 = 0, $95 = 0, $96 = 0;
+ var $97 = 0, $99 = 0, $100 = 0, $101 = 0, $102 = 0, $$etemp$15 = 0, $$etemp$14$0 = 0, $$etemp$14$1 = 0;
+ var $st$16$0 = 0, $st$17$1 = 0, $105 = 0, $106 = 0, $107 = 0, $108 = 0, $109 = 0, $110 = 0;
+ var $112 = 0, $113 = 0, $114 = 0, $115 = 0, $116 = 0, $117 = 0, $118 = 0, $119 = 0;
+ var $121 = 0, $123 = 0, $_r1_sroa_0_0_insert_ext$0 = 0, $_r1_sroa_0_0_insert_ext$1 = 0, $$etemp$18$0 = 0, $$etemp$18$1 = 0, $_r1_sroa_0_0_insert_mask$0 = 0, $_r1_sroa_0_0_insert_mask$1 = 0;
+ var $_r1_sroa_0_0_insert_insert$0 = 0, $_r1_sroa_0_0_insert_insert$1 = 0, $124 = 0, $125 = 0, $126 = 0, $_old = 0, $_r3_sroa_0_0_load242 = +0, $ld$19$0 = 0;
+ var $_r3_sroa_0_0_load242$$SHADOW$0 = 0, $ld$20$1 = 0, $_r3_sroa_0_0_load242$$SHADOW$1 = 0, $_r2_sroa_0_0_cast284 = 0, $_r2_sroa_0_0_load265_pre = +0, $ld$21$0 = 0, $_r2_sroa_0_0_load265_pre$$SHADOW$0 = 0, $ld$22$1 = 0;
+ var $_r2_sroa_0_0_load265_pre$$SHADOW$1 = 0, $_r3_sroa_0_0_cast264_pre = 0, $_pre = 0, $_pre300 = 0;
+ var label = 0;
+ var __stackBase__ = 0;
+ __stackBase__ = STACKTOP;
+ STACKTOP = STACKTOP + 16 | 0;
+ $_r2_sroa_0 = __stackBase__ | 0;
+ $_r3_sroa_0 = __stackBase__ + 8 | 0;
+ $1 = HEAP32[(114668 | 0) >> 2] | 0;
+ $2 = ($1 | 0) == 0;
+ if ($2) {
+ HEAP32[(114664 | 0) >> 2] = 1;
+ HEAP32[(114668 | 0) >> 2] = 1;
+ $$etemp$1 = 114672 | 0;
+ $$etemp$0$0 = -1;
+ $$etemp$0$1 = -1;
+ $st$2$0 = $$etemp$1 | 0;
+ HEAP32[$st$2$0 >> 2] = $$etemp$0$0;
+ $st$3$1 = $$etemp$1 + 4 | 0;
+ HEAP32[$st$3$1 >> 2] = $$etemp$0$1;
+ HEAP32[(114684 | 0) >> 2] = 25296 | 0;
+ HEAP32[(114704 | 0) >> 2] = 110728;
+ HEAP32[(114712 | 0) >> 2] = 8;
+ HEAP32[(114784 | 0 | 0) >> 2] = HEAP32[(107856 | 0 | 0) >> 2] | 0;
+ HEAP32[(114784 | 0 | 0) + 4 >> 2] = HEAP32[(107856 | 0 | 0) + 4 >> 2] | 0;
+ HEAP32[(114784 | 0 | 0) + 8 >> 2] = HEAP32[(107856 | 0 | 0) + 8 >> 2] | 0;
+ HEAP32[(114784 | 0 | 0) + 12 >> 2] = HEAP32[(107856 | 0 | 0) + 12 >> 2] | 0;
+ HEAP32[(114784 | 0 | 0) + 16 >> 2] = HEAP32[(107856 | 0 | 0) + 16 >> 2] | 0;
+ HEAP32[(114784 | 0 | 0) + 20 >> 2] = HEAP32[(107856 | 0 | 0) + 20 >> 2] | 0;
+ }
+ $5 = HEAP32[138960 >> 2] | 0;
+ $6 = _org_xmlvm_runtime_XMLVMArray_createSingleDimension___java_lang_Class_int($5, 25) | 0;
+ $7 = $me + 8 | 0;
+ $8 = $me + 20 | 0;
+ $9 = $8;
+ $10 = HEAP32[$9 >> 2] | 0;
+ $_r1_sroa_0_0_insert_ext191$0 = $10;
+ $_r1_sroa_0_0_insert_ext191$1 = 0;
+ $11 = (HEAP32[tempDoublePtr >> 2] = $_r1_sroa_0_0_insert_ext191$0, HEAP32[tempDoublePtr + 4 >> 2] = $_r1_sroa_0_0_insert_ext191$1, +HEAPF64[tempDoublePtr >> 3]);
+ $12 = ($10 | 0) > -1;
+ if ($12) {
+ $_r2_sroa_0_0_cast284 = $_r2_sroa_0;
+ HEAP32[$_r2_sroa_0_0_cast284 >> 2] = 0;
+ $_r2_sroa_0_0_load265_pre = +HEAPF64[$_r2_sroa_0 >> 3];
+ $ld$21$0 = $_r2_sroa_0 | 0;
+ $_r2_sroa_0_0_load265_pre$$SHADOW$0 = HEAP32[$ld$21$0 >> 2] | 0;
+ $ld$22$1 = $_r2_sroa_0 + 4 | 0;
+ $_r2_sroa_0_0_load265_pre$$SHADOW$1 = HEAP32[$ld$22$1 >> 2] | 0;
+ $_r3_sroa_0_0_cast264_pre = $_r3_sroa_0;
+ $_pre = $6 + 16 | 0;
+ $_pre300 = $_pre;
+ var $_r2_sroa_0_0_load265 = $_r2_sroa_0_0_load265_pre;
+ var $_r3_sroa_0_0_cast264_pre_phi = $_r3_sroa_0_0_cast264_pre;
+ var $_pre_phi301 = $_pre300;
+ } else {
+ $14 = $6 + 16 | 0;
+ $15 = $14;
+ $16 = HEAP32[$15 >> 2] | 0;
+ $17 = $16;
+ HEAP16[$17 >> 1] = 48;
+ $_r2_sroa_0_0_cast283 = $_r2_sroa_0;
+ $18 = HEAP32[$15 >> 2] | 0;
+ $19 = $18 + 2 | 0;
+ $20 = $19;
+ HEAP16[$20 >> 1] = 46;
+ HEAP32[$_r2_sroa_0_0_cast283 >> 2] = 2;
+ $21 = $10 + 1 | 0;
+ $_r3_sroa_0_0_cast247 = $_r3_sroa_0;
+ HEAP32[$_r3_sroa_0_0_cast247 >> 2] = $21;
+ $_r3_sroa_0_0_load244 = +HEAPF64[$_r3_sroa_0 >> 3];
+ $ld$4$0 = $_r3_sroa_0 | 0;
+ $_r3_sroa_0_0_load244$$SHADOW$0 = HEAP32[$ld$4$0 >> 2] | 0;
+ $ld$5$1 = $_r3_sroa_0 + 4 | 0;
+ $_r3_sroa_0_0_load244$$SHADOW$1 = HEAP32[$ld$5$1 >> 2] | 0;
+ $_r2_sroa_0_0_load = +HEAPF64[$_r2_sroa_0 >> 3];
+ $ld$6$0 = $_r2_sroa_0 | 0;
+ $_r2_sroa_0_0_load$$SHADOW$0 = HEAP32[$ld$6$0 >> 2] | 0;
+ $ld$7$1 = $_r2_sroa_0 + 4 | 0;
+ $_r2_sroa_0_0_load$$SHADOW$1 = HEAP32[$ld$7$1 >> 2] | 0;
+ HEAPF64[$_r3_sroa_0 >> 3] = $_r2_sroa_0_0_load;
+ HEAPF64[$_r2_sroa_0 >> 3] = $_r3_sroa_0_0_load244;
+ $22$0 = $_r3_sroa_0_0_load244$$SHADOW$0;
+ $22$1 = $_r3_sroa_0_0_load244$$SHADOW$1;
+ $trunc297$0 = $22$0;
+ $trunc297 = $trunc297$0;
+ $23 = ($trunc297 | 0) < 0;
+ $24$0 = $_r2_sroa_0_0_load$$SHADOW$0;
+ $24$1 = $_r2_sroa_0_0_load$$SHADOW$1;
+ $25$0 = $24$0;
+ $25 = $25$0;
+ if ($23) {
+ $26 = $trunc297 + 1 | 0;
+ $27 = ($26 | 0) > 0;
+ $smax = $27 ? $26 : 0;
+ $28 = $25 + $smax | 0;
+ var $113 = $25;
+ var $112 = $trunc297;
+ while (1) {
+ $114 = $113 + 1 | 0;
+ $115 = HEAP32[$15 >> 2] | 0;
+ $116 = $115;
+ $117 = $116 + ($113 << 1) | 0;
+ HEAP16[$117 >> 1] = 48;
+ $118 = $112 + 1 | 0;
+ $119 = ($118 | 0) < 0;
+ if ($119) {
+ var $113 = $114;
+ var $112 = $118;
+ } else {
+ break;
+ }
+ }
+ $29 = $28 - $trunc297 | 0;
+ HEAP32[$_r3_sroa_0_0_cast247 >> 2] = $29;
+ HEAP32[$_r2_sroa_0_0_cast283 >> 2] = $smax;
+ $_r3_sroa_0_0_load239_pre = +HEAPF64[$_r3_sroa_0 >> 3];
+ $ld$8$0 = $_r3_sroa_0 | 0;
+ $_r3_sroa_0_0_load239_pre$$SHADOW$0 = HEAP32[$ld$8$0 >> 2] | 0;
+ $ld$9$1 = $_r3_sroa_0 + 4 | 0;
+ $_r3_sroa_0_0_load239_pre$$SHADOW$1 = HEAP32[$ld$9$1 >> 2] | 0;
+ $_r3_sroa_0_0_load239 = $_r3_sroa_0_0_load239_pre;
+ } else {
+ $_r3_sroa_0_0_load239 = $_r2_sroa_0_0_load;
+ }
+ HEAPF64[$_r2_sroa_0 >> 3] = $_r3_sroa_0_0_load239;
+ var $_r2_sroa_0_0_load265 = $_r3_sroa_0_0_load239;
+ var $_r3_sroa_0_0_cast264_pre_phi = $_r3_sroa_0_0_cast247;
+ var $_pre_phi301 = $15;
+ }
+ $32 = $me + 16 | 0;
+ $33 = $32;
+ $34 = HEAP32[$33 >> 2] | 0;
+ $_r3_sroa_0_0_cast253 = $_r3_sroa_0;
+ HEAP32[$_r3_sroa_0_0_cast253 >> 2] = $34;
+ $35 = $me + 12 | 0;
+ $36 = $35;
+ $37 = HEAP32[$36 >> 2] | 0;
+ $38 = $37 + 1 | 0;
+ HEAP32[$36 >> 2] = $38;
+ $39 = $34 + 16 | 0;
+ $40 = $39;
+ $41 = HEAP32[$40 >> 2] | 0;
+ $42 = $41;
+ $43 = $42 + ($37 << 2) | 0;
+ $44 = HEAP32[$43 >> 2] | 0;
+ HEAP32[$_r3_sroa_0_0_cast264_pre_phi >> 2] = $44;
+ $_r3_sroa_0_0_load243 = +HEAPF64[$_r3_sroa_0 >> 3];
+ $ld$10$0 = $_r3_sroa_0 | 0;
+ $_r3_sroa_0_0_load243$$SHADOW$0 = HEAP32[$ld$10$0 >> 2] | 0;
+ $ld$11$1 = $_r3_sroa_0 + 4 | 0;
+ $_r3_sroa_0_0_load243$$SHADOW$1 = HEAP32[$ld$11$1 >> 2] | 0;
+ HEAPF64[$_r3_sroa_0 >> 3] = $_r2_sroa_0_0_load265;
+ HEAPF64[$_r2_sroa_0 >> 3] = $11;
+ $_r2_sroa_0_0_cast = $_r2_sroa_0;
+ $45 = $7;
+ var $_r1_sroa_0_0 = $_r3_sroa_0_0_load243;
+ var $_r2_sroa_0_0_load266287 = $10;
+ var $_r3_sroa_0_0_load241 = $_r2_sroa_0_0_load265;
+ var $_sink_in = $_r2_sroa_0_0_load265;
+ while (1) {
+ HEAPF64[tempDoublePtr >> 3] = $_sink_in;
+ var $_sink$0 = HEAP32[tempDoublePtr >> 2] | 0;
+ var $_sink$1 = HEAP32[tempDoublePtr + 4 >> 2] | 0;
+ $47$0 = $_sink$0;
+ $47 = $47$0;
+ HEAPF64[tempDoublePtr >> 3] = $_r1_sroa_0_0;
+ var $48$0 = HEAP32[tempDoublePtr >> 2] | 0;
+ var $48$1 = HEAP32[tempDoublePtr + 4 >> 2] | 0;
+ $_r1_sroa_0_0_extract_trunc185$0 = $48$0;
+ $_r1_sroa_0_0_extract_trunc185 = $_r1_sroa_0_0_extract_trunc185$0;
+ $49 = ($_r1_sroa_0_0_extract_trunc185 | 0) == -1;
+ do {
+ if ($49) {
+ $121 = ($_r2_sroa_0_0_load266287 | 0) < -1;
+ if ($121) {
+ $_r1_sroa_0_2 = $_r3_sroa_0_0_load241;
+ break;
+ }
+ $123 = $47 + 1 | 0;
+ $_r1_sroa_0_0_insert_ext$0 = $123;
+ $_r1_sroa_0_0_insert_ext$1 = 0;
+ $$etemp$18$0 = 0;
+ $$etemp$18$1 = -1;
+ $_r1_sroa_0_0_insert_mask$0 = $48$0 & $$etemp$18$0;
+ $_r1_sroa_0_0_insert_mask$1 = $48$1 & $$etemp$18$1;
+ $_r1_sroa_0_0_insert_insert$0 = $_r1_sroa_0_0_insert_ext$0 | $_r1_sroa_0_0_insert_mask$0;
+ $_r1_sroa_0_0_insert_insert$1 = $_r1_sroa_0_0_insert_ext$1 | $_r1_sroa_0_0_insert_mask$1;
+ $124 = HEAP32[$_pre_phi301 >> 2] | 0;
+ $125 = $124;
+ $126 = $125 + ($47 << 1) | 0;
+ HEAP16[$126 >> 1] = 48;
+ var $_r1_sroa_0_1_in$1 = $_r1_sroa_0_0_insert_insert$1;
+ var $_r1_sroa_0_1_in$0 = $_r1_sroa_0_0_insert_insert$0;
+ label = 785;
+ break;
+ } else {
+ $51 = $47 + 1 | 0;
+ $52 = $_r1_sroa_0_0_extract_trunc185 + 48 | 0;
+ $53 = $52 & 65535;
+ $54 = HEAP32[$_pre_phi301 >> 2] | 0;
+ $55 = $54;
+ $56 = $55 + ($47 << 1) | 0;
+ HEAP16[$56 >> 1] = $53;
+ $_r1_sroa_0_0_insert_ext195$0 = $51;
+ $_r1_sroa_0_0_insert_ext195$1 = 0;
+ var $_r1_sroa_0_1_in$1 = $_r1_sroa_0_0_insert_ext195$1;
+ var $_r1_sroa_0_1_in$0 = $_r1_sroa_0_0_insert_ext195$0;
+ label = 785;
+ break;
+ }
+ } while (0);
+ do {
+ if ((label | 0) == 785) {
+ label = 0;
+ $_r1_sroa_0_1 = (HEAP32[tempDoublePtr >> 2] = $_r1_sroa_0_1_in$0, HEAP32[tempDoublePtr + 4 >> 2] = $_r1_sroa_0_1_in$1, +HEAPF64[tempDoublePtr >> 3]);
+ $58 = ($_r2_sroa_0_0_load266287 | 0) == 0;
+ if (!$58) {
+ $_r1_sroa_0_2 = $_r1_sroa_0_1;
+ break;
+ }
+ $_r1_sroa_0_0_extract_trunc169$0 = $_r1_sroa_0_1_in$0;
+ $_r1_sroa_0_0_extract_trunc169 = $_r1_sroa_0_0_extract_trunc169$0;
+ $60 = $_r1_sroa_0_0_extract_trunc169 + 1 | 0;
+ HEAP32[$_r3_sroa_0_0_cast264_pre_phi >> 2] = $60;
+ $61 = HEAP32[$_pre_phi301 >> 2] | 0;
+ $62 = $61;
+ $63 = $62 + ($_r1_sroa_0_0_extract_trunc169 << 1) | 0;
+ HEAP16[$63 >> 1] = 46;
+ $_r3_sroa_0_0_load240 = +HEAPF64[$_r3_sroa_0 >> 3];
+ $ld$12$0 = $_r3_sroa_0 | 0;
+ $_r3_sroa_0_0_load240$$SHADOW$0 = HEAP32[$ld$12$0 >> 2] | 0;
+ $ld$13$1 = $_r3_sroa_0 + 4 | 0;
+ $_r3_sroa_0_0_load240$$SHADOW$1 = HEAP32[$ld$13$1 >> 2] | 0;
+ $_r1_sroa_0_2 = $_r3_sroa_0_0_load240;
+ }
+ } while (0);
+ $64 = $_r2_sroa_0_0_load266287 - 1 | 0;
+ $65 = HEAP32[$36 >> 2] | 0;
+ HEAP32[$_r3_sroa_0_0_cast264_pre_phi >> 2] = $65;
+ $66 = HEAP32[$45 >> 2] | 0;
+ $67 = ($65 | 0) < ($66 | 0);
+ if ($67) {
+ $69 = HEAP32[$33 >> 2] | 0;
+ HEAP32[$_r3_sroa_0_0_cast253 >> 2] = $69;
+ $70 = $65 + 1 | 0;
+ HEAP32[$36 >> 2] = $70;
+ $71 = $69 + 16 | 0;
+ $72 = $71;
+ $73 = HEAP32[$72 >> 2] | 0;
+ $74 = $73;
+ $75 = $74 + ($65 << 2) | 0;
+ $76 = HEAP32[$75 >> 2] | 0;
+ HEAP32[$_r3_sroa_0_0_cast264_pre_phi >> 2] = $76;
+ $phitmp = ($76 | 0) != -1;
+ $77 = ($64 | 0) > -2;
+ $or_cond = $phitmp | $77;
+ if (!$or_cond) {
+ break;
+ }
+ } else {
+ HEAP32[$_r3_sroa_0_0_cast264_pre_phi >> 2] = -1;
+ $_old = ($64 | 0) > -2;
+ if (!$_old) {
+ break;
+ }
+ }
+ $_r3_sroa_0_0_load242 = +HEAPF64[$_r3_sroa_0 >> 3];
+ $ld$19$0 = $_r3_sroa_0 | 0;
+ $_r3_sroa_0_0_load242$$SHADOW$0 = HEAP32[$ld$19$0 >> 2] | 0;
+ $ld$20$1 = $_r3_sroa_0 + 4 | 0;
+ $_r3_sroa_0_0_load242$$SHADOW$1 = HEAP32[$ld$20$1 >> 2] | 0;
+ HEAPF64[$_r3_sroa_0 >> 3] = $_r1_sroa_0_2;
+ var $_r1_sroa_0_0 = $_r3_sroa_0_0_load242;
+ var $_r2_sroa_0_0_load266287 = $64;
+ var $_r3_sroa_0_0_load241 = $_r1_sroa_0_2;
+ var $_sink_in = $_r1_sroa_0_2;
+ }
+ HEAP32[$_r2_sroa_0_0_cast >> 2] = $64;
+ $79 = HEAP32[(106148 | 0) >> 2] | 0;
+ $80 = ($79 | 0) == 0;
+ if ($80) {
+ ___INIT_java_lang_String();
+ }
+ $82 = _GC_MALLOC(36 | 0) | 0;
+ $83 = $82;
+ HEAP32[$83 >> 2] = 106144;
+ $84 = $82 + 4 | 0;
+ _memset($84 | 0 | 0, 0 | 0 | 0, 32 | 0 | 0);
+ $_r2_sroa_0_0_cast269 = $_r2_sroa_0;
+ HEAP32[$_r2_sroa_0_0_cast269 >> 2] = $82;
+ HEAPF64[tempDoublePtr >> 3] = $_r1_sroa_0_2;
+ var $85$0 = HEAP32[tempDoublePtr >> 2] | 0;
+ var $85$1 = HEAP32[tempDoublePtr + 4 >> 2] | 0;
+ $_r1_sroa_0_0_extract_trunc$0 = $85$0;
+ $_r1_sroa_0_0_extract_trunc = $_r1_sroa_0_0_extract_trunc$0;
+ $86 = $82 + 8 | 0;
+ $87 = $86;
+ HEAP32[$87 >> 2] = 0;
+ $88 = $82 + 12 | 0;
+ $89 = $88;
+ HEAP32[$89 >> 2] = 0;
+ $90 = $82 + 16 | 0;
+ $91 = $90;
+ HEAP32[$91 >> 2] = 0;
+ $92 = ($_r1_sroa_0_0_extract_trunc | 0) < 0;
+ if ($92) {
+ _XMLVM_ERROR(16136 | 0, 13208 | 0, 132112 | 0, 830);
+ return 0 | 0;
+ }
+ $94 = $6 + 12 | 0;
+ $95 = $94;
+ $96 = HEAP32[$95 >> 2] | 0;
+ $97 = ($96 | 0) < ($_r1_sroa_0_0_extract_trunc | 0);
+ if ($97) {
+ _XMLVM_ERROR(16136 | 0, 13208 | 0, 132112 | 0, 830);
+ return 0 | 0;
+ }
+ $99 = $82 + 24 | 0;
+ $100 = $99;
+ HEAP32[$100 >> 2] = 0;
+ $101 = HEAP32[(114668 | 0) >> 2] | 0;
+ $102 = ($101 | 0) == 0;
+ if (!$102) {
+ $105 = HEAP32[138960 >> 2] | 0;
+ $106 = _org_xmlvm_runtime_XMLVMArray_createSingleDimension___java_lang_Class_int($105, $_r1_sroa_0_0_extract_trunc) | 0;
+ $107 = $82 + 20 | 0;
+ $108 = $107;
+ HEAP32[$108 >> 2] = $106;
+ $109 = $82 + 28 | 0;
+ $110 = $109;
+ HEAP32[$110 >> 2] = $_r1_sroa_0_0_extract_trunc;
+ _java_lang_System_arraycopy___java_lang_Object_int_java_lang_Object_int_int($6, 0, $106, 0, $_r1_sroa_0_0_extract_trunc);
+ STACKTOP = __stackBase__;
+ return $82 | 0;
+ }
+ HEAP32[(114664 | 0) >> 2] = 1;
+ HEAP32[(114668 | 0) >> 2] = 1;
+ $$etemp$15 = 114672 | 0;
+ $$etemp$14$0 = -1;
+ $$etemp$14$1 = -1;
+ $st$16$0 = $$etemp$15 | 0;
+ HEAP32[$st$16$0 >> 2] = $$etemp$14$0;
+ $st$17$1 = $$etemp$15 + 4 | 0;
+ HEAP32[$st$17$1 >> 2] = $$etemp$14$1;
+ HEAP32[(114684 | 0) >> 2] = 25296 | 0;
+ HEAP32[(114704 | 0) >> 2] = 110728;
+ HEAP32[(114712 | 0) >> 2] = 8;
+ HEAP32[(114784 | 0 | 0) >> 2] = HEAP32[(107856 | 0 | 0) >> 2] | 0;
+ HEAP32[(114784 | 0 | 0) + 4 >> 2] = HEAP32[(107856 | 0 | 0) + 4 >> 2] | 0;
+ HEAP32[(114784 | 0 | 0) + 8 >> 2] = HEAP32[(107856 | 0 | 0) + 8 >> 2] | 0;
+ HEAP32[(114784 | 0 | 0) + 12 >> 2] = HEAP32[(107856 | 0 | 0) + 12 >> 2] | 0;
+ HEAP32[(114784 | 0 | 0) + 16 >> 2] = HEAP32[(107856 | 0 | 0) + 16 >> 2] | 0;
+ HEAP32[(114784 | 0 | 0) + 20 >> 2] = HEAP32[(107856 | 0 | 0) + 20 >> 2] | 0;
+ $105 = HEAP32[138960 >> 2] | 0;
+ $106 = _org_xmlvm_runtime_XMLVMArray_createSingleDimension___java_lang_Class_int($105, $_r1_sroa_0_0_extract_trunc) | 0;
+ $107 = $82 + 20 | 0;
+ $108 = $107;
+ HEAP32[$108 >> 2] = $106;
+ $109 = $82 + 28 | 0;
+ $110 = $109;
+ HEAP32[$110 >> 2] = $_r1_sroa_0_0_extract_trunc;
+ _java_lang_System_arraycopy___java_lang_Object_int_java_lang_Object_int_int($6, 0, $106, 0, $_r1_sroa_0_0_extract_trunc);
+ STACKTOP = __stackBase__;
+ return $82 | 0;
+}
+function __ZN23b2EdgeAndPolygonContact8EvaluateEP10b2ManifoldRK11b2TransformS4_($this, $manifold, $xfA, $xfB) {
+ $this = $this | 0;
+ $manifold = $manifold | 0;
+ $xfA = $xfA | 0;
+ $xfB = $xfB | 0;
+ var $collider_i = 0, $1 = 0, $2 = 0, $3 = 0, $4 = 0, $5 = 0, $6 = 0, $7 = 0;
+ var $8 = 0, $9 = 0, $10 = 0, $11 = 0;
+ var label = 0;
+ var __stackBase__ = 0;
+ __stackBase__ = STACKTOP;
+ STACKTOP = STACKTOP + 256 | 0;
+ $collider_i = __stackBase__ | 0;
+ $1 = $this + 48 | 0;
+ $2 = HEAP32[$1 >> 2] | 0;
+ $3 = $2 + 12 | 0;
+ $4 = HEAP32[$3 >> 2] | 0;
+ $5 = $4;
+ $6 = $this + 52 | 0;
+ $7 = HEAP32[$6 >> 2] | 0;
+ $8 = $7 + 12 | 0;
+ $9 = HEAP32[$8 >> 2] | 0;
+ $10 = $9;
+ $11 = $collider_i;
+ __ZN12b2EPCollider7CollideEP10b2ManifoldPK11b2EdgeShapeRK11b2TransformPK14b2PolygonShapeS7_($collider_i, $manifold, $5, $xfA, $10, $xfB);
+ STACKTOP = __stackBase__;
+ return;
+}
+// EMSCRIPTEN_GENERATED_FUNCTIONS: ["asm", "__Z11printResultPiS_j", "_segment_holding", "__ZN5identC2EiPKcPci", "_vec2Length", "exc", "label", "confuusion", "tempDouble", "_org_apache_harmony_luni_util_NumberConverter_freeFormat__", "__ZN23b2EdgeAndPolygonContact8EvaluateEP10b2ManifoldRK11b2TransformS4_"]
diff --git a/tools/js-optimizer.js b/tools/js-optimizer.js
index 56ff971c..ce67da89 100644
--- a/tools/js-optimizer.js
+++ b/tools/js-optimizer.js
@@ -1787,6 +1787,7 @@ function eliminate(ast, memSafe) {
if (asm) var asmData = normalizeAsm(func);
//printErr('eliminate in ' + func[1]);
+
// First, find the potentially eliminatable functions: that have one definition and one use
var definitions = {};
var uses = {};
@@ -1802,6 +1803,7 @@ function eliminate(ast, memSafe) {
}
}
// examine body and note locals
+ var hasSwitch = false;
traverse(func, function(node, type) {
if (type === 'var') {
var node1 = node[1];
@@ -1833,11 +1835,29 @@ function eliminate(ast, memSafe) {
uses[name]--; // because the name node will show up by itself in the previous case
}
}
+ } else if (type == 'switch') {
+ hasSwitch = true;
}
});
+
+ // we cannot eliminate variables if there is a switch
+ if (traverse(func, function(node, type) {
+ if (type == 'switch') return true;
+ })) {
+ if (asm) denormalizeAsm(func, asmData);
+ return;
+ }
+
var potentials = {}; // local variables with 1 definition and 1 use
var sideEffectFree = {}; // whether a local variable has no side effects in its definition
- for (var name in locals) {
+
+ function unprocessVariable(name) {
+ if (name in potentials) delete potentials[name];
+ if (name in varsToRemove) delete varsToRemove[name];
+ if (name in sideEffectFree) delete sideEffectFree[name];
+ if (name in varsToTryToRemove) delete varsToTryToRemove[name];
+ }
+ function processVariable(name) {
if (definitions[name] == 1 && uses[name] == 1) {
potentials[name] = 1;
} else if (uses[name] == 0 && (!definitions[name] || definitions[name] <= 1)) { // no uses, no def or 1 def (cannot operate on phis, and the llvm optimizer will remove unneeded phis anyhow)
@@ -1862,11 +1882,32 @@ function eliminate(ast, memSafe) {
if (!hasSideEffects) {
varsToRemove[name] = !definitions[name] ? 2 : 1; // remove it normally
sideEffectFree[name] = true;
+ // Each time we remove a variable with 0 uses, if its value has no
+ // side effects and vanishes too, then we can remove a use from variables
+ // appearing in it, and possibly eliminate again
+ if (value) {
+ traverse(value, function(node, type) {
+ if (type == 'name') {
+ var name = node[1];
+ node[1] = ''; // we can remove this - it will never be shown, and should not be left to confuse us as we traverse
+ if (name in locals) {
+ uses[name]--; // cannot be infinite recursion since we descend an energy function
+ assert(uses[name] >= 0);
+ unprocessVariable(name);
+ processVariable(name);
+ }
+ }
+ });
+ }
} else {
varsToTryToRemove[name] = 1; // try to remove it later during scanning
}
}
}
+ for (var name in locals) {
+ processVariable(name);
+ }
+
//printErr('defs: ' + JSON.stringify(definitions));
//printErr('uses: ' + JSON.stringify(uses));
//printErr('values: ' + JSON.stringify(values));
diff --git a/tools/shared.py b/tools/shared.py
index 5a9860db..cc056074 100644
--- a/tools/shared.py
+++ b/tools/shared.py
@@ -509,6 +509,9 @@ COMPILER_OPTS = COMPILER_OPTS + ['-m32', '-U__i386__', '-U__i386', '-Ui386',
'-D__IEEE_LITTLE_ENDIAN', '-fno-math-errno', '-fno-threadsafe-statics',
'-target', LLVM_TARGET]
+if LLVM_TARGET == 'le32-unknown-nacl':
+ COMPILER_OPTS += ['-U__native_client__', '-U__pnacl__', '-U__ELF__'] # The nacl target is originally used for Google Native Client. Emscripten is not NaCl, so remove the platform #define, when using their triple.
+
USE_EMSDK = not os.environ.get('EMMAKEN_NO_SDK')
if USE_EMSDK:
@@ -675,6 +678,7 @@ class Settings:
Settings.RELOOP = 1
if opt_level >= 3:
# Aside from these, -O3 also runs closure compiler and llvm lto
+ Settings.FORCE_ALIGNED_MEMORY = 1
Settings.DOUBLE_MODE = 0
Settings.PRECISE_I64_MATH = 0
if noisy: logging.warning('Applying some potentially unsafe optimizations! (Use -O2 if this fails.)')