summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAlon Zakai <alonzakai@gmail.com>2013-06-20 18:15:36 -0700
committerAlon Zakai <alonzakai@gmail.com>2013-06-20 18:15:36 -0700
commitc3ed656997ea4515d846debf45121af1bd174a51 (patch)
treede84436eba40aedf96ca8c091c743e0d7d79e965
parent0ad87244178badf26cd5c8e0ed88116e87026472 (diff)
parent97d19be7f46bb3b0862e575fc6e06abafca74df7 (diff)
Merge branch 'incoming'
-rw-r--r--AUTHORS5
-rwxr-xr-xemcc17
-rwxr-xr-xemscripten.py22
-rw-r--r--src/fastLong.js18
-rw-r--r--src/jsifier.js15
-rw-r--r--src/library.js25
-rw-r--r--src/library_browser.js7
-rw-r--r--src/library_sdl.js37
-rw-r--r--src/parseTools.js10
-rw-r--r--src/relooper/Relooper.cpp2
-rw-r--r--src/runtime.js6
-rw-r--r--system/include/bsd/float.h18
-rw-r--r--system/include/libc/sys/dirent.h16
-rw-r--r--system/lib/libc.symbols2
-rw-r--r--system/lib/libc/gen/warn.c2
-rw-r--r--tests/float+.c143
-rw-r--r--tests/hello_world_gles_deriv.c7
-rw-r--r--tests/hello_world_sdl.cpp8
-rw-r--r--tests/lua/binarytrees.lua17
-rw-r--r--tests/lua/scimark.lua50
-rwxr-xr-xtests/runner.py297
-rw-r--r--tests/sdl_audio_mix.c12
-rw-r--r--tests/sdl_canvas.c2
-rw-r--r--tests/sdl_canvas_blank.c17
-rw-r--r--tests/sdl_canvas_blank.pngbin0 -> 914 bytes
-rw-r--r--tests/sdl_canvas_twice.c4
-rw-r--r--tests/sdl_image_prepare_data.c4
-rw-r--r--tests/sdl_maprgba.c1
-rw-r--r--tests/sounds/noise.oggbin0 -> 9205 bytes
-rw-r--r--tools/file_packager.py42
-rw-r--r--tools/js-optimizer.js87
-rw-r--r--tools/shared.py19
-rw-r--r--tools/test-js-optimizer-asm-pre-output.js364
-rw-r--r--tools/test-js-optimizer-asm-pre.js361
34 files changed, 1390 insertions, 247 deletions
diff --git a/AUTHORS b/AUTHORS
index 9e9d5748..27206740 100644
--- a/AUTHORS
+++ b/AUTHORS
@@ -83,6 +83,5 @@ a license to everyone to use it as detailed in LICENSE.)
* Jez Ng <me@jezng.com>
* Marc Feeley <mfeeley@mozilla.com> (copyright owned by Mozilla Foundation)
* Ludovic Perrine <jazzzz@gmail.com>
-
-
-
+* David Barksdale <david.barksdale@adcedosolutions.com>
+* Manfred Manik Nerurkar <nerurkar*at*made-apps.biz> (copyright owned by MADE, GmbH)
diff --git a/emcc b/emcc
index 2a7e10d0..b8230e95 100755
--- a/emcc
+++ b/emcc
@@ -53,8 +53,6 @@ from tools import shared
from tools.shared import Compression, execute, suffix, unsuffixed, unsuffixed_basename
from tools.response_file import read_response_file
-logging = logging.getLogger('emcc')
-
# Mapping of emcc opt levels to llvm opt levels. We use llvm opt level 3 in emcc opt
# levels 2 and 3 (emcc 3 is unsafe opts, so unsuitable for the only level to get
# llvm opt level 3, and speed-wise emcc level 2 is already the slowest/most optimizing
@@ -819,8 +817,12 @@ try:
newargs[i] = ''
elif newargs[i] == '-v':
shared.COMPILER_OPTS += ['-v']
- DEBUG = 1
os.environ['EMCC_DEBUG'] = '1' # send to child processes too
+ if DEBUG != 1:
+ # swap in debug logging
+ DEBUG = 1
+ shared.set_logging()
+ logging.debug('invocation: ' + ' '.join(sys.argv))
newargs[i] = ''
elif newargs[i].startswith('--shell-file'):
check_bad_eq(newargs[i])
@@ -853,9 +855,10 @@ try:
memory_init_file = int(newargs[i+1])
newargs[i] = ''
newargs[i+1] = ''
- elif newargs[i].startswith(('-I/', '-L/')):
- if not absolute_warning_shown:
- logging.warning ('-I or -L of an absolute path encountered. If this is to a local system header/library, it may cause problems (local system files make sense for compiling natively on your system, but not necessarily to JavaScript)') # Of course an absolute path to a non-system-specific library or header is fine, and you can ignore this warning. The danger are system headers that are e.g. x86 specific and nonportable. The emscripten bundled headers are modified to be portable, local system ones are generally not
+ elif newargs[i].startswith(('-I', '-L')):
+ path_name = newargs[i][2:]
+ if not absolute_warning_shown and os.path.isabs(path_name):
+ logging.warning ('-I or -L of an absolute path "' + newargs[i] + '" encountered. If this is to a local system header/library, it may cause problems (local system files make sense for compiling natively on your system, but not necessarily to JavaScript)') # Of course an absolute path to a non-system-specific library or header is fine, and you can ignore this warning. The danger are system headers that are e.g. x86 specific and nonportable. The emscripten bundled headers are modified to be portable, local system ones are generally not
absolute_warning_shown = True
newargs = [ arg for arg in newargs if arg is not '' ]
@@ -902,7 +905,7 @@ try:
if i > 0:
prev = newargs[i-1]
- if prev in ['-MT', '-install_name', '-I', '-L']: continue # ignore this gcc-style argument
+ if prev in ['-MT', '-MF', '-MQ', '-D', '-U', '-o', '-x', '-Xpreprocessor', '-include', '-imacros', '-idirafter', '-iprefix', '-iwithprefix', '-iwithprefixbefore', '-isysroot', '-imultilib', '-A', '-isystem', '-iquote', '-install_name', '-I', '-L']: continue # ignore this gcc-style argument
if (os.path.islink(arg) and os.path.realpath(arg).endswith(SOURCE_SUFFIXES + BITCODE_SUFFIXES + DYNAMICLIB_SUFFIXES + ASSEMBLY_SUFFIXES)):
arg = os.path.realpath(arg)
diff --git a/emscripten.py b/emscripten.py
index d8312855..56f59273 100755
--- a/emscripten.py
+++ b/emscripten.py
@@ -128,7 +128,7 @@ def emscript(infile, settings, outfile, libraries=[], compiler_engine=None,
if DEBUG: print >> sys.stderr, ' emscript: split took %s seconds' % (time.time() - t)
if len(funcs) == 0:
- raise RuntimeError('No functions to process. Make sure you prevented LLVM from eliminating them as dead (use EXPORTED_FUNCTIONS if necessary, see the FAQ)')
+ print >> sys.stderr, 'No functions to process. Make sure you prevented LLVM from eliminating them as dead (use EXPORTED_FUNCTIONS if necessary, see the FAQ)'
#if DEBUG:
# print >> sys.stderr, '========= pre ================\n'
@@ -407,7 +407,7 @@ def emscript(infile, settings, outfile, libraries=[], compiler_engine=None,
math_envs = ['Math.min'] # TODO: move min to maths
asm_setup += '\n'.join(['var %s = %s;' % (f.replace('.', '_'), f) for f in math_envs])
- basic_funcs = ['abort', 'assert', 'asmPrintInt', 'asmPrintFloat', 'copyTempDouble', 'copyTempFloat'] + [m.replace('.', '_') for m in math_envs]
+ basic_funcs = ['abort', 'assert', 'asmPrintInt', 'asmPrintFloat'] + [m.replace('.', '_') for m in math_envs]
if settings['RESERVED_FUNCTION_POINTERS'] > 0: basic_funcs.append('jsCall')
if settings['SAFE_HEAP']: basic_funcs += ['SAFE_HEAP_LOAD', 'SAFE_HEAP_STORE', 'SAFE_HEAP_CLEAR']
if settings['CHECK_HEAP_ALIGN']: basic_funcs += ['CHECK_ALIGN_2', 'CHECK_ALIGN_4', 'CHECK_ALIGN_8']
@@ -555,6 +555,24 @@ var asm = (function(global, env, buffer) {
threwValue = value;
}
}
+ function copyTempFloat(ptr) {
+ ptr = ptr|0;
+ HEAP8[tempDoublePtr] = HEAP8[ptr];
+ HEAP8[tempDoublePtr+1|0] = HEAP8[ptr+1|0];
+ HEAP8[tempDoublePtr+2|0] = HEAP8[ptr+2|0];
+ HEAP8[tempDoublePtr+3|0] = HEAP8[ptr+3|0];
+ }
+ function copyTempDouble(ptr) {
+ ptr = ptr|0;
+ HEAP8[tempDoublePtr] = HEAP8[ptr];
+ HEAP8[tempDoublePtr+1|0] = HEAP8[ptr+1|0];
+ HEAP8[tempDoublePtr+2|0] = HEAP8[ptr+2|0];
+ HEAP8[tempDoublePtr+3|0] = HEAP8[ptr+3|0];
+ HEAP8[tempDoublePtr+4|0] = HEAP8[ptr+4|0];
+ HEAP8[tempDoublePtr+5|0] = HEAP8[ptr+5|0];
+ HEAP8[tempDoublePtr+6|0] = HEAP8[ptr+6|0];
+ HEAP8[tempDoublePtr+7|0] = HEAP8[ptr+7|0];
+ }
''' + ''.join(['''
function setTempRet%d(value) {
value = value|0;
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 156fd65d..e9bc9a79 100644
--- a/src/jsifier.js
+++ b/src/jsifier.js
@@ -328,7 +328,7 @@ function JSify(data, functionsOnly, givenFunctions) {
var js = (index !== null ? '' : item.ident + '=') + constant;
if (js) js += ';';
- if (!ASM_JS && (EXPORT_ALL || (item.ident in EXPORTED_GLOBALS))) {
+ if (!ASM_JS && NAMED_GLOBALS && (EXPORT_ALL || (item.ident in EXPORTED_GLOBALS))) {
js += '\nModule["' + item.ident + '"] = ' + item.ident + ';';
}
if (BUILD_AS_SHARED_LIB == 2 && !item.private_) {
@@ -1185,8 +1185,13 @@ function JSify(data, functionsOnly, givenFunctions) {
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 +1315,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) + ')';
});
diff --git a/src/library.js b/src/library.js
index f958a436..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',
@@ -4657,6 +4657,14 @@ LibraryManager.library = {
return 0;
},
+ strnlen: function(ptr, num) {
+ for (var i = 0; i < num; i++) {
+ if ({{{ makeGetValue('ptr', 0, 'i8') }}} == 0) return i;
+ ptr++;
+ }
+ return num;
+ },
+
strstr: function(ptr1, ptr2) {
var check = 0, start;
do {
@@ -4991,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 9800fedf..925b64e2 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 a131f424..356c9746 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...
@@ -965,6 +961,13 @@ var LibrarySDL = {
return SDL.makeSurface(width, height, flags, false, 'CreateRGBSurface', rmask, gmask, bmask, amask);
},
+ SDL_CreateRGBSurfaceFrom: function(pixels, width, height, depth, pitch, rmask, gmask, bmask, amask) {
+ // TODO: Actually fill pixel data to created surface.
+ // TODO: Take into account depth and pitch parameters.
+ console.log('TODO: Partially unimplemented SDL_CreateRGBSurfaceFrom called!');
+ return SDL.makeSurface(width, height, 0, false, 'CreateRGBSurfaceFrom', rmask, gmask, bmask, amask);
+ },
+
SDL_DisplayFormatAlpha: function(surf) {
var oldData = SDL.surfaces[surf];
var ret = SDL.makeSurface(oldData.width, oldData.height, oldData.flags, false, 'copy:' + oldData.source);
@@ -1113,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() {
@@ -1810,7 +1813,7 @@ var LibrarySDL = {
SDL_AddTimer: function(interval, callback, param) {
return window.setTimeout(function() {
- Runtime.dynCall('ii', callback, [interval, param]);
+ Runtime.dynCall('iii', callback, [interval, param]);
}, interval);
},
SDL_RemoveTimer: function(id) {
@@ -1837,9 +1840,9 @@ var LibrarySDL = {
Mix_FadeOutChannel: function() { throw 'Mix_FadeOutChannel' },
Mix_Linked_Version: function() { throw 'Mix_Linked_Version: TODO' },
- SDL_CreateRGBSurfaceFrom: function() { throw 'SDL_CreateRGBSurfaceFrom: TODO' },
SDL_SaveBMP_RW: function() { throw 'SDL_SaveBMP_RW: TODO' },
+ SDL_WM_SetIcon: function() { /* This function would set the application window icon surface, which doesn't apply for web canvases, so a no-op. */ },
SDL_HasRDTSC: function() { return 0; },
SDL_HasMMX: function() { return 0; },
SDL_HasMMXExt: function() { return 0; },
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 8a6e18b8..7ceeb2f8 100644
--- a/src/relooper/Relooper.cpp
+++ b/src/relooper/Relooper.cpp
@@ -897,6 +897,7 @@ void Relooper::Calculate(Block *Entry) {
BlockSet Entries;
Entries.insert(Entry);
Root = Analyzer(this).Process(AllBlocks, Entries, NULL);
+ assert(Root);
// Post optimizations
@@ -1091,6 +1092,7 @@ void Relooper::Calculate(Block *Entry) {
void Relooper::Render() {
OutputBuffer = OutputBufferRoot;
+ assert(Root);
Root->Render(false);
}
diff --git a/src/runtime.js b/src/runtime.js
index 9bedfe68..e6d5f962 100644
--- a/src/runtime.js
+++ b/src/runtime.js
@@ -25,7 +25,7 @@ var RuntimeGenerator = {
sep = sep || ';';
var ret = RuntimeGenerator.alloc(size, 'STACK', false, sep, USE_TYPED_ARRAYS != 2 || (isNumber(size) && parseInt(size) % {{{ STACK_ALIGN }}} == 0));
if (ASSERTIONS) {
- ret += sep + 'assert(' + asmCoercion('(STACKTOP|0) < (STACK_MAX|0)', 'i32') + ')';
+ ret += sep + '(assert(' + asmCoercion('(STACKTOP|0) < (STACK_MAX|0)', 'i32') + ')|0)';
}
return ret;
},
@@ -37,11 +37,11 @@ var RuntimeGenerator = {
if (USE_TYPED_ARRAYS == 2) {
assert(initial % Runtime.STACK_ALIGN == 0);
if (ASSERTIONS && Runtime.STACK_ALIGN == 4) {
- ret += '; assert(' + asmCoercion('!(STACKTOP&3)', 'i32') + ')';
+ ret += '; (assert(' + asmCoercion('!(STACKTOP&3)', 'i32') + ')|0)';
}
}
if (ASSERTIONS) {
- ret += '; assert(' + asmCoercion('(STACKTOP|0) < (STACK_MAX|0)', 'i32') + ')';
+ ret += '; (assert(' + asmCoercion('(STACKTOP|0) < (STACK_MAX|0)', 'i32') + ')|0)';
}
if (false) {
ret += '; _memset(' + asmCoercion('__stackBase__', 'i32') + ', 0, ' + initial + ')';
diff --git a/system/include/bsd/float.h b/system/include/bsd/float.h
index 7020cf9a..383e637c 100644
--- a/system/include/bsd/float.h
+++ b/system/include/bsd/float.h
@@ -73,15 +73,15 @@ __END_DECLS
#define DBL_MAX 1.7976931348623157E+308
#define DBL_MAX_10_EXP 308
-#define LDBL_MANT_DIG 64
-#define LDBL_EPSILON 1.08420217248550443401e-19L
-#define LDBL_DIG 18
-#define LDBL_MIN_EXP (-16381)
-#define LDBL_MIN 3.36210314311209350626e-4932L
-#define LDBL_MIN_10_EXP (-4931)
-#define LDBL_MAX_EXP 16384
-#define LDBL_MAX 1.18973149535723176502e+4932L
-#define LDBL_MAX_10_EXP 4932
+#define LDBL_MANT_DIG DBL_MANT_DIG
+#define LDBL_EPSILON DBL_EPSILON
+#define LDBL_DIG DBL_DIG
+#define LDBL_MIN_EXP DBL_MIN_EXP
+#define LDBL_MIN DBL_MIN
+#define LDBL_MIN_10_EXP DBL_MIN_10_EXP
+#define LDBL_MAX_EXP DBL_MAX_EXP
+#define LDBL_MAX DBL_MAX
+#define LDBL_MAX_10_EXP DBL_MAX_10_EXP
#if __ISO_C_VISIBLE >= 1999
#define DECIMAL_DIG 21
diff --git a/system/include/libc/sys/dirent.h b/system/include/libc/sys/dirent.h
index 9dcf34d1..0d8b02b5 100644
--- a/system/include/libc/sys/dirent.h
+++ b/system/include/libc/sys/dirent.h
@@ -34,8 +34,22 @@ int scandir(const char *dirp,
enum {
DT_UNKNOWN = 0,
#define DT_UNKNOWN DT_UNKNOWN
- DT_DIR = 4
+ DT_FIFO = 1,
+#define DT_FIFO DT_FIFO
+ DT_CHR = 2,
+#define DT_CHR DT_CHR
+ DT_DIR = 4,
#define DT_DIR DT_DIR
+ DT_BLK = 6,
+#define DT_BLK DT_BLK
+ DT_REG = 8,
+#define DT_REG DT_REG
+ DT_LNK = 10,
+#define DT_LNK DT_LNK
+ DT_SOCK = 12,
+#define DT_SOCK DT_SOCK
+ DT_WHT = 14
+#define DT_WHT DT_WHT
};
#ifdef __cplusplus
diff --git a/system/lib/libc.symbols b/system/lib/libc.symbols
index 70b21024..561f01c1 100644
--- a/system/lib/libc.symbols
+++ b/system/lib/libc.symbols
@@ -77,5 +77,5 @@
W verrx
W vwarn
W vwarnx
- W warn1
+ W warn
W warnx
diff --git a/system/lib/libc/gen/warn.c b/system/lib/libc/gen/warn.c
index c0803ab9..c0dd2cd7 100644
--- a/system/lib/libc/gen/warn.c
+++ b/system/lib/libc/gen/warn.c
@@ -46,4 +46,4 @@ _warn(const char *fmt, ...)
/* PRINTFLIKE1 */
void
-warn(const char *fmt, ...) __attribute__((weak, alias("warn")));
+warn(const char *fmt, ...) __attribute__((weak, alias("_warn")));
diff --git a/tests/float+.c b/tests/float+.c
new file mode 100644
index 00000000..eab08262
--- /dev/null
+++ b/tests/float+.c
@@ -0,0 +1,143 @@
+/* Supplemental information about the floating-point formats.
+ Copyright (C) 2007, 2009, 2010 Free Software Foundation, Inc.
+ Written by Bruno Haible <bruno@clisp.org>, 2007.
+
+ This program is free software; you can redistribute it and/or modify
+ it under the terms of the GNU Lesser General Public License as published by
+ the Free Software Foundation; either version 2, or (at your option)
+ any later version.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU Lesser General Public License for more details.
+
+ You should have received a copy of the GNU Lesser General Public License
+ along with this program; if not, write to the Free Software Foundation,
+ Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */
+
+#include <float.h>
+#include <limits.h>
+
+/* Number of bits in the mantissa of a floating-point number, including the
+ "hidden bit". */
+#if FLT_RADIX == 2
+# define FLT_MANT_BIT FLT_MANT_DIG
+# define DBL_MANT_BIT DBL_MANT_DIG
+# define LDBL_MANT_BIT LDBL_MANT_DIG
+#elif FLT_RADIX == 4
+# define FLT_MANT_BIT (FLT_MANT_DIG * 2)
+# define DBL_MANT_BIT (DBL_MANT_DIG * 2)
+# define LDBL_MANT_BIT (LDBL_MANT_DIG * 2)
+#elif FLT_RADIX == 16
+# define FLT_MANT_BIT (FLT_MANT_DIG * 4)
+# define DBL_MANT_BIT (DBL_MANT_DIG * 4)
+# define LDBL_MANT_BIT (LDBL_MANT_DIG * 4)
+#endif
+
+/* Bit mask that can be used to mask the exponent, as an unsigned number. */
+#define FLT_EXP_MASK ((FLT_MAX_EXP - FLT_MIN_EXP) | 7)
+#define DBL_EXP_MASK ((DBL_MAX_EXP - DBL_MIN_EXP) | 7)
+#define LDBL_EXP_MASK ((LDBL_MAX_EXP - LDBL_MIN_EXP) | 7)
+
+/* Number of bits used for the exponent of a floating-point number, including
+ the exponent's sign. */
+#define FLT_EXP_BIT \
+ (FLT_EXP_MASK < 0x100 ? 8 : \
+ FLT_EXP_MASK < 0x200 ? 9 : \
+ FLT_EXP_MASK < 0x400 ? 10 : \
+ FLT_EXP_MASK < 0x800 ? 11 : \
+ FLT_EXP_MASK < 0x1000 ? 12 : \
+ FLT_EXP_MASK < 0x2000 ? 13 : \
+ FLT_EXP_MASK < 0x4000 ? 14 : \
+ FLT_EXP_MASK < 0x8000 ? 15 : \
+ FLT_EXP_MASK < 0x10000 ? 16 : \
+ FLT_EXP_MASK < 0x20000 ? 17 : \
+ FLT_EXP_MASK < 0x40000 ? 18 : \
+ FLT_EXP_MASK < 0x80000 ? 19 : \
+ FLT_EXP_MASK < 0x100000 ? 20 : \
+ FLT_EXP_MASK < 0x200000 ? 21 : \
+ FLT_EXP_MASK < 0x400000 ? 22 : \
+ FLT_EXP_MASK < 0x800000 ? 23 : \
+ FLT_EXP_MASK < 0x1000000 ? 24 : \
+ FLT_EXP_MASK < 0x2000000 ? 25 : \
+ FLT_EXP_MASK < 0x4000000 ? 26 : \
+ FLT_EXP_MASK < 0x8000000 ? 27 : \
+ FLT_EXP_MASK < 0x10000000 ? 28 : \
+ FLT_EXP_MASK < 0x20000000 ? 29 : \
+ FLT_EXP_MASK < 0x40000000 ? 30 : \
+ FLT_EXP_MASK <= 0x7fffffff ? 31 : \
+ 32)
+#define DBL_EXP_BIT \
+ (DBL_EXP_MASK < 0x100 ? 8 : \
+ DBL_EXP_MASK < 0x200 ? 9 : \
+ DBL_EXP_MASK < 0x400 ? 10 : \
+ DBL_EXP_MASK < 0x800 ? 11 : \
+ DBL_EXP_MASK < 0x1000 ? 12 : \
+ DBL_EXP_MASK < 0x2000 ? 13 : \
+ DBL_EXP_MASK < 0x4000 ? 14 : \
+ DBL_EXP_MASK < 0x8000 ? 15 : \
+ DBL_EXP_MASK < 0x10000 ? 16 : \
+ DBL_EXP_MASK < 0x20000 ? 17 : \
+ DBL_EXP_MASK < 0x40000 ? 18 : \
+ DBL_EXP_MASK < 0x80000 ? 19 : \
+ DBL_EXP_MASK < 0x100000 ? 20 : \
+ DBL_EXP_MASK < 0x200000 ? 21 : \
+ DBL_EXP_MASK < 0x400000 ? 22 : \
+ DBL_EXP_MASK < 0x800000 ? 23 : \
+ DBL_EXP_MASK < 0x1000000 ? 24 : \
+ DBL_EXP_MASK < 0x2000000 ? 25 : \
+ DBL_EXP_MASK < 0x4000000 ? 26 : \
+ DBL_EXP_MASK < 0x8000000 ? 27 : \
+ DBL_EXP_MASK < 0x10000000 ? 28 : \
+ DBL_EXP_MASK < 0x20000000 ? 29 : \
+ DBL_EXP_MASK < 0x40000000 ? 30 : \
+ DBL_EXP_MASK <= 0x7fffffff ? 31 : \
+ 32)
+#define LDBL_EXP_BIT \
+ (LDBL_EXP_MASK < 0x100 ? 8 : \
+ LDBL_EXP_MASK < 0x200 ? 9 : \
+ LDBL_EXP_MASK < 0x400 ? 10 : \
+ LDBL_EXP_MASK < 0x800 ? 11 : \
+ LDBL_EXP_MASK < 0x1000 ? 12 : \
+ LDBL_EXP_MASK < 0x2000 ? 13 : \
+ LDBL_EXP_MASK < 0x4000 ? 14 : \
+ LDBL_EXP_MASK < 0x8000 ? 15 : \
+ LDBL_EXP_MASK < 0x10000 ? 16 : \
+ LDBL_EXP_MASK < 0x20000 ? 17 : \
+ LDBL_EXP_MASK < 0x40000 ? 18 : \
+ LDBL_EXP_MASK < 0x80000 ? 19 : \
+ LDBL_EXP_MASK < 0x100000 ? 20 : \
+ LDBL_EXP_MASK < 0x200000 ? 21 : \
+ LDBL_EXP_MASK < 0x400000 ? 22 : \
+ LDBL_EXP_MASK < 0x800000 ? 23 : \
+ LDBL_EXP_MASK < 0x1000000 ? 24 : \
+ LDBL_EXP_MASK < 0x2000000 ? 25 : \
+ LDBL_EXP_MASK < 0x4000000 ? 26 : \
+ LDBL_EXP_MASK < 0x8000000 ? 27 : \
+ LDBL_EXP_MASK < 0x10000000 ? 28 : \
+ LDBL_EXP_MASK < 0x20000000 ? 29 : \
+ LDBL_EXP_MASK < 0x40000000 ? 30 : \
+ LDBL_EXP_MASK <= 0x7fffffff ? 31 : \
+ 32)
+
+/* Number of bits used for a floating-point number: the mantissa (not
+ counting the "hidden bit", since it may or may not be explicit), the
+ exponent, and the sign. */
+#define FLT_TOTAL_BIT ((FLT_MANT_BIT - 1) + FLT_EXP_BIT + 1)
+#define DBL_TOTAL_BIT ((DBL_MANT_BIT - 1) + DBL_EXP_BIT + 1)
+#define LDBL_TOTAL_BIT ((LDBL_MANT_BIT - 1) + LDBL_EXP_BIT + 1)
+
+/* Number of bytes used for a floating-point number.
+ This can be smaller than the 'sizeof'. For example, on i386 systems,
+ 'long double' most often have LDBL_MANT_BIT = 64, LDBL_EXP_BIT = 16, hence
+ LDBL_TOTAL_BIT = 80 bits, i.e. 10 bytes of consecutive memory, but
+ sizeof (long double) = 12 or = 16. */
+#define SIZEOF_FLT ((FLT_TOTAL_BIT + CHAR_BIT - 1) / CHAR_BIT)
+#define SIZEOF_DBL ((DBL_TOTAL_BIT + CHAR_BIT - 1) / CHAR_BIT)
+#define SIZEOF_LDBL ((LDBL_TOTAL_BIT + CHAR_BIT - 1) / CHAR_BIT)
+
+/* Verify that SIZEOF_FLT <= sizeof (float) etc. */
+typedef int verify_sizeof_flt[2 * (SIZEOF_FLT <= sizeof (float)) - 1];
+typedef int verify_sizeof_dbl[2 * (SIZEOF_DBL <= sizeof (double)) - 1];
+typedef int verify_sizeof_ldbl[2 * (SIZEOF_LDBL <= sizeof (long double)) - 1];
diff --git a/tests/hello_world_gles_deriv.c b/tests/hello_world_gles_deriv.c
index 2e0f0664..c5354d4e 100644
--- a/tests/hello_world_gles_deriv.c
+++ b/tests/hello_world_gles_deriv.c
@@ -46,8 +46,13 @@
#include <string.h>
#include <sys/time.h>
#include <unistd.h>
+#ifdef __APPLE__
+#include <OpenGL/gl.h>
+#include <Glut/glut.h>
+#else
#include <GL/gl.h>
#include <GL/glut.h>
+#endif
#ifndef HAVE_BUILTIN_SINCOS
#include "sincos.h"
@@ -716,7 +721,7 @@ main(int argc, char *argv[])
glutCreateWindow("es2gears");
/* Set up glut callback functions */
- gears_idle();
+ glutIdleFunc (gears_idle);
glutReshapeFunc(gears_reshape);
glutDisplayFunc(gears_draw);
glutSpecialFunc(gears_special);
diff --git a/tests/hello_world_sdl.cpp b/tests/hello_world_sdl.cpp
index b6401995..eeaad0cd 100644
--- a/tests/hello_world_sdl.cpp
+++ b/tests/hello_world_sdl.cpp
@@ -2,7 +2,7 @@
#include <SDL/SDL.h>
-int main() {
+extern "C" int main(int argc, char** argv) {
printf("hello, world!\n");
SDL_Init(SDL_INIT_VIDEO);
@@ -11,10 +11,8 @@ int main() {
if (SDL_MUSTLOCK(screen)) SDL_LockSurface(screen);
for (int i = 0; i < 256; i++) {
for (int j = 0; j < 256; j++) {
- *((char*)screen->pixels + i*256*4 + j*4 + 0) = i;
- *((char*)screen->pixels + i*256*4 + j*4 + 1) = j;
- *((char*)screen->pixels + i*256*4 + j*4 + 2) = 255-i;
- *((char*)screen->pixels + i*256*4 + j*4 + 3) = (i+j)%255; // actually ignored, since this is to the screen
+ // alpha component is actually ignored, since this is to the screen
+ *((Uint32*)screen->pixels + i * 256 + j) = SDL_MapRGBA(screen->format, i, j, 255-i, (i+j) % 255);
}
}
if (SDL_MUSTLOCK(screen)) SDL_UnlockSurface(screen);
diff --git a/tests/lua/binarytrees.lua b/tests/lua/binarytrees.lua
index 2ae3dd69..58c0ce87 100644
--- a/tests/lua/binarytrees.lua
+++ b/tests/lua/binarytrees.lua
@@ -21,7 +21,22 @@ local function ItemCheck(tree)
end
end
-local N = tonumber(arg and arg[1]) or 0
+local N = tonumber(arg and arg[1]) or 4
+
+if N == 0 then
+ N = 0
+elseif N == 1 then
+ N = 9.5
+elseif N == 2 then
+ N = 11.99
+elseif N == 3 then
+ N = 12.85
+elseif N == 4 then
+ N = 14.72
+elseif N == 5 then
+ N = 15.82
+end
+
local mindepth = 4
local maxdepth = mindepth + 2
if maxdepth < N then maxdepth = N end
diff --git a/tests/lua/scimark.lua b/tests/lua/scimark.lua
index 7e37c219..34fbc4ff 100644
--- a/tests/lua/scimark.lua
+++ b/tests/lua/scimark.lua
@@ -387,31 +387,31 @@ end
--printf("Lua SciMark %s based on SciMark 2.0a. %s.\n\n",
-- SCIMARK_VERSION, SCIMARK_COPYRIGHT)
-while arg and arg[1] do
- local a = table.remove(arg, 1)
- if a == "-noffi" then
- package.preload.ffi = nil
- elseif a == "-small" then
- SIZE_SELECT = "small"
- elseif a == "-large" then
- SIZE_SELECT = "large"
- elseif benchmarks[a] then
- local p = benchmarks[SIZE_SELECT][a]
- measure(MIN_TIME, a, tonumber(arg[1]) or p[1], tonumber(arg[2]) or p[2])
- return
- else
- printf("Usage: scimark [-noffi] [-small|-large] [BENCH params...]\n\n")
- printf("BENCH -small -large\n")
- printf("---------------------------------------\n")
- for _,name in ipairs(benchmarks) do
- printf("%-7s %-13s %s\n", name,
- fmtparams(unpack(benchmarks.small[name])),
- fmtparams(unpack(benchmarks.large[name])))
- end
- printf("\n")
- os.exit(1)
- end
-end
+--while arg and arg[1] do
+-- local a = table.remove(arg, 1)
+-- if a == "-noffi" then
+-- package.preload.ffi = nil
+-- elseif a == "-small" then
+-- SIZE_SELECT = "small"
+-- elseif a == "-large" then
+-- SIZE_SELECT = "large"
+-- elseif benchmarks[a] then
+-- local p = benchmarks[SIZE_SELECT][a]
+-- measure(MIN_TIME, a, tonumber(arg[1]) or p[1], tonumber(arg[2]) or p[2])
+-- return
+-- else
+-- printf("Usage: scimark [-noffi] [-small|-large] [BENCH params...]\n\n")
+-- printf("BENCH -small -large\n")
+-- printf("---------------------------------------\n")
+-- for _,name in ipairs(benchmarks) do
+-- printf("%-7s %-13s %s\n", name,
+-- fmtparams(unpack(benchmarks.small[name])),
+-- fmtparams(unpack(benchmarks.large[name])))
+-- end
+-- printf("\n")
+-- os.exit(1)
+-- end
+--end
local params = benchmarks[SIZE_SELECT]
local sum = 0
diff --git a/tests/runner.py b/tests/runner.py
index 5e101024..bcd8e84c 100755
--- a/tests/runner.py
+++ b/tests/runner.py
@@ -133,7 +133,7 @@ class RunnerCore(unittest.TestCase):
# Hardcode in the arguments, so js is portable without manual commandlinearguments
if not args: return
js = open(filename).read()
- open(filename, 'w').write(js.replace('run();', 'run(%s);' % str(args)))
+ open(filename, 'w').write(js.replace('run();', 'run(%s + Module["arguments"]);' % str(args)))
def prep_ll_run(self, filename, ll_file, force_recompile=False, build_ll_hook=None):
if ll_file.endswith(('.bc', '.o')):
@@ -3982,6 +3982,11 @@ Exiting setjmp function, level: 0, prev_jmp: -1
'''
self.do_run(src, '*2,2,5,8,8***8,8,5,8,8***7,2,6,990,7,2*', [], lambda x, err: x.replace('\n', '*'))
+ def test_float_h(self):
+ process = Popen([PYTHON, EMCC, path_from_root('tests', 'float+.c')], stdout=PIPE, stderr=PIPE)
+ process.communicate()
+ assert process.returncode is 0, 'float.h should agree with our system'
+
def test_emscripten_api(self):
#if Settings.MICRO_OPTS or Settings.RELOOP or Building.LLVM_OPTS: return self.skip('FIXME')
@@ -4018,7 +4023,7 @@ def process(filename):
double get() {
double ret = 0;
- __asm __volatile__("12/3.3":"=r"(ret));
+ __asm __volatile__("Math.abs(-12/3.3)":"=r"(ret)); // write to a variable
return ret;
}
@@ -4031,6 +4036,39 @@ def process(filename):
self.do_run(src, 'Inline JS is very cool\n3.64')
+ def zzztest_inlinejs2(self):
+ if Settings.ASM_JS: return self.skip('asm does not support random code, TODO: something that works in asm')
+ src = r'''
+ #include <stdio.h>
+
+ double get() {
+ double ret = 0;
+ __asm __volatile__("Math.abs(-12/3.3)":"=r"(ret)); // write to a variable
+ return ret;
+ }
+
+ int mix(int x, int y) {
+ int ret;
+ asm("Math.pow(2, %0+%1+1)" : "=r"(ret) : "r"(x), "r"(y)); // read and write
+ return ret;
+ }
+
+ void mult() {
+ asm("var $_$1 = Math.abs(-100); $_$1 *= 2;"); // multiline
+ asm __volatile__("Module.print($_$1); Module.print('\n')");
+ }
+
+ int main(int argc, char **argv) {
+ asm("Module.print('Inline JS is very cool')");
+ printf("%.2f\n", get());
+ printf("%d\n", mix(argc, argc/2));
+ mult();
+ return 0;
+ }
+ '''
+
+ self.do_run(src, 'Inline JS is very cool\n3.64\nwaka\nzakai\n')
+
def test_memorygrowth(self):
if Settings.USE_TYPED_ARRAYS == 0: return self.skip('memory growth is only supported with typed arrays')
if Settings.ASM_JS: return self.skip('asm does not support memory growth yet')
@@ -4273,6 +4311,7 @@ def process(filename):
def test_varargs(self):
if Settings.QUANTUM_SIZE == 1: return self.skip('FIXME: Add support for this')
+ if not self.is_le32(): return self.skip('we do not support all varargs stuff without le32')
src = '''
#include <stdio.h>
@@ -4305,6 +4344,53 @@ def process(filename):
puts(d);
va_end(v);
}
+
+ void varargs_listoffsets_list_evaluate(int count, va_list ap, int vaIteration)
+ {
+ while(count > 0)
+ {
+ const char* string = va_arg(ap, const char*);
+ printf("%s", string);
+ count--;
+ }
+ printf("\\n");
+ }
+
+ void varags_listoffsets_list_copy(int count, va_list ap, int iteration)
+ {
+ va_list ap_copy;
+ va_copy(ap_copy, ap);
+ varargs_listoffsets_list_evaluate(count, ap_copy, iteration);
+ va_end(ap_copy);
+ }
+
+ void varargs_listoffsets_args(int type, int count, ...)
+ {
+ va_list ap;
+ va_start(ap, count);
+
+ // evaluate a copied list
+ varags_listoffsets_list_copy(count, ap, 1);
+ varags_listoffsets_list_copy(count, ap, 2);
+ varags_listoffsets_list_copy(count, ap, 3);
+ varags_listoffsets_list_copy(count, ap, 4);
+
+ varargs_listoffsets_list_evaluate(count, ap, 1);
+
+ // NOTE: we expect this test to fail, so we will check the stdout for <BAD+0><BAD+1>.....
+ varargs_listoffsets_list_evaluate(count, ap, 2);
+
+ // NOTE: this test has to work again, as we restart the list
+ va_end(ap);
+ va_start(ap, count);
+ varargs_listoffsets_list_evaluate(count, ap, 3);
+ va_end(ap);
+ }
+
+ void varargs_listoffsets_main()
+ {
+ varargs_listoffsets_args(0, 5, "abc", "def", "ghi", "jkl", "mno", "<BAD+0>", "<BAD+1>", "<BAD+2>", "<BAD+3>", "<BAD+4>", "<BAD+5>", "<BAD+6>", "<BAD+7>", "<BAD+8>", "<BAD+9>", "<BAD+10>", "<BAD+11>", "<BAD+12>", "<BAD+13>", "<BAD+14>", "<BAD+15>", "<BAD+16>");
+ }
#define GETMAX(pref, type) \
type getMax##pref(int num, ...) \
@@ -4337,10 +4423,14 @@ def process(filename):
void (*vfp)(const char *s, ...) = argc == 1211 ? NULL : vary;
vfp("*vfp:%d,%d*", 22, 199);
+ // ensure lists work properly when copied, reinited etc.
+ varargs_listoffsets_main();
+
return 0;
}
'''
- self.do_run(src, '*cheez: 0+24*\n*cheez: 0+24*\n*albeit*\n*albeit*\nQ85*\nmaxxi:21*\nmaxxD:22.10*\n*vfp:22,199*\n*vfp:22,199*\n')
+ self.do_run(src, '*cheez: 0+24*\n*cheez: 0+24*\n*albeit*\n*albeit*\nQ85*\nmaxxi:21*\nmaxxD:22.10*\n*vfp:22,199*\n*vfp:22,199*\n'+
+ 'abcdefghijklmno\nabcdefghijklmno\nabcdefghijklmno\nabcdefghijklmno\nabcdefghijklmno\n<BAD+0><BAD+1><BAD+2><BAD+3><BAD+4>\nabcdefghijklmno\n')
def test_varargs_byval(self):
if Settings.USE_TYPED_ARRAYS != 2: return self.skip('FIXME: Add support for this')
@@ -10496,6 +10586,24 @@ f.close()
self.assertContained('result: 1', run_js(os.path.join(self.get_dir(), 'a.out.js')))
+ def test_export_all(self):
+ lib = r'''
+ #include <stdio.h>
+ void libf1() { printf("libf1\n"); }
+ void libf2() { printf("libf2\n"); }
+ '''
+ lib_name = os.path.join(self.get_dir(), 'lib.c')
+ open(lib_name, 'w').write(lib)
+
+ open('main.js', 'w').write('''
+ _libf1();
+ _libf2();
+ ''')
+
+ Building.emcc(lib_name, ['-s', 'EXPORT_ALL=1', '--post-js', 'main.js'], output_filename='a.out.js')
+
+ self.assertContained('libf1\nlibf2\n', run_js(os.path.join(self.get_dir(), 'a.out.js')))
+
def test_abspaths(self):
# Includes with absolute paths are generally dangerous, things like -I/usr/.. will get to system local headers, not our portable ones.
@@ -10507,7 +10615,7 @@ f.close()
(['-Lsubdir/something'], False),
([], False)]:
err = Popen([PYTHON, EMCC, 'main.c'] + args, stderr=PIPE).communicate()[1]
- assert ('-I or -L of an absolute path encountered. If this is to a local system header/library, it may cause problems (local system files make sense for compiling natively on your system, but not necessarily to JavaScript)' in err) == expected, err
+ assert ('encountered. If this is to a local system header/library, it may cause problems (local system files make sense for compiling natively on your system, but not necessarily to JavaScript)' in err) == expected, err
def test_local_link(self):
# Linking a local library directly, like /usr/lib/libsomething.so, cannot work of course since it
@@ -11434,6 +11542,9 @@ elif 'browser' in str(sys.argv):
result = q.get()
s.wfile.write(result)
s.wfile.close()
+ def log_request(code=0, size=0):
+ # don't log; too noisy
+ pass
httpd = BaseHTTPServer.HTTPServer(('localhost', 9999), TestServerHandler)
httpd.serve_forever() # test runner will kill us
@@ -11454,6 +11565,9 @@ elif 'browser' in str(sys.argv):
s.send_response(500)
s.send_header("Content-type", "text/html")
s.end_headers()
+ def log_request(code=0, size=0):
+ # don't log; too noisy
+ pass
os.chdir(dir)
httpd = BaseHTTPServer.HTTPServer(('localhost', 8888), TestServerHandler)
httpd.serve_forever() # test runner will kill us
@@ -11469,7 +11583,8 @@ elif 'browser' in str(sys.argv):
print '[Browser harness server on process %d]' % browser.harness_server.pid
webbrowser.open_new('http://localhost:9999/run_harness')
- def __del__(self):
+ @classmethod
+ def tearDownClass(cls):
if not hasattr(browser, 'harness_server'): return
browser.harness_server.terminate()
@@ -11580,9 +11695,8 @@ elif 'browser' in str(sys.argv):
def test_html(self):
# test HTML generation.
- self.reftest(path_from_root('tests', 'htmltest.png'))
- output = Popen([PYTHON, EMCC, path_from_root('tests', 'hello_world_sdl.cpp'), '-o', 'something.html', '--pre-js', 'reftest.js']).communicate()
- self.run_browser('something.html', 'You should see "hello, world!" and a colored cube.', '/report_result?0')
+ self.btest('hello_world_sdl.cpp', reference='htmltest.png',
+ message='You should see "hello, world!" and a colored cube.')
def build_native_lzma(self):
lzma_native = path_from_root('third_party', 'lzma.js', 'lzma-native')
@@ -11804,6 +11918,9 @@ elif 'browser' in str(sys.argv):
def test_preload_file(self):
absolute_src_path = os.path.join(self.get_dir(), 'somefile.txt').replace('\\', '/')
open(absolute_src_path, 'w').write('''load me right before running the code please''')
+
+ absolute_src_path2 = os.path.join(self.get_dir(), '.somefile.txt').replace('\\', '/')
+ open(absolute_src_path2, 'w').write('''load me right before running the code please''')
def make_main(path):
print path
@@ -11828,6 +11945,7 @@ elif 'browser' in str(sys.argv):
test_cases = [
# (source preload-file string, file on target FS to load)
("somefile.txt", "somefile.txt"),
+ (".somefile.txt@somefile.txt", "somefile.txt"),
("./somefile.txt", "somefile.txt"),
("somefile.txt@file.txt", "file.txt"),
("./somefile.txt@file.txt", "file.txt"),
@@ -11856,11 +11974,13 @@ elif 'browser' in str(sys.argv):
# Test subdirectory handling with asset packaging.
os.makedirs(os.path.join(self.get_dir(), 'assets/sub/asset1/').replace('\\', '/'))
+ os.makedirs(os.path.join(self.get_dir(), 'assets/sub/asset1/.git').replace('\\', '/')) # Test adding directory that shouldn't exist.
os.makedirs(os.path.join(self.get_dir(), 'assets/sub/asset2/').replace('\\', '/'))
open(os.path.join(self.get_dir(), 'assets/sub/asset1/file1.txt'), 'w').write('''load me right before running the code please''')
+ open(os.path.join(self.get_dir(), 'assets/sub/asset1/.git/shouldnt_be_embedded.txt'), 'w').write('''this file should not get embedded''')
open(os.path.join(self.get_dir(), 'assets/sub/asset2/file2.txt'), 'w').write('''load me right before running the code please''')
absolute_assets_src_path = os.path.join(self.get_dir(), 'assets').replace('\\', '/')
- def make_main_two_files(path1, path2):
+ def make_main_two_files(path1, path2, nonexistingpath):
open(os.path.join(self.get_dir(), 'main.cpp'), 'w').write(self.with_report_result(r'''
#include <stdio.h>
#include <string.h>
@@ -11879,24 +11999,29 @@ elif 'browser' in str(sys.argv):
if (f == NULL)
result = 0;
fclose(f);
+
+ f = fopen("%s", "r");
+ if (f != NULL)
+ result = 0;
+
REPORT_RESULT();
return 0;
}
- ''' % (path1, path2)))
+ ''' % (path1, path2, nonexistingpath)))
test_cases = [
- # (source directory to embed, file1 on target FS to load, file2 on target FS to load)
- ("assets", "assets/sub/asset1/file1.txt", "assets/sub/asset2/file2.txt"),
- ("assets/", "assets/sub/asset1/file1.txt", "assets/sub/asset2/file2.txt"),
- ("assets@/", "/sub/asset1/file1.txt", "/sub/asset2/file2.txt"),
- ("assets/@/", "/sub/asset1/file1.txt", "/sub/asset2/file2.txt"),
- ("assets@./", "/sub/asset1/file1.txt", "/sub/asset2/file2.txt"),
- (absolute_assets_src_path + "@/", "/sub/asset1/file1.txt", "/sub/asset2/file2.txt"),
- (absolute_assets_src_path + "@/assets", "/assets/sub/asset1/file1.txt", "/assets/sub/asset2/file2.txt")]
+ # (source directory to embed, file1 on target FS to load, file2 on target FS to load, name of a file that *shouldn't* exist on VFS)
+ ("assets", "assets/sub/asset1/file1.txt", "assets/sub/asset2/file2.txt", "assets/sub/asset1/.git/shouldnt_be_embedded.txt"),
+ ("assets/", "assets/sub/asset1/file1.txt", "assets/sub/asset2/file2.txt", "assets/sub/asset1/.git/shouldnt_be_embedded.txt"),
+ ("assets@/", "/sub/asset1/file1.txt", "/sub/asset2/file2.txt", "/sub/asset1/.git/shouldnt_be_embedded.txt"),
+ ("assets/@/", "/sub/asset1/file1.txt", "/sub/asset2/file2.txt", "/sub/asset1/.git/shouldnt_be_embedded.txt"),
+ ("assets@./", "/sub/asset1/file1.txt", "/sub/asset2/file2.txt", "/sub/asset1/.git/shouldnt_be_embedded.txt"),
+ (absolute_assets_src_path + "@/", "/sub/asset1/file1.txt", "/sub/asset2/file2.txt", "/sub/asset1/.git/shouldnt_be_embedded.txt"),
+ (absolute_assets_src_path + "@/assets", "/assets/sub/asset1/file1.txt", "/assets/sub/asset2/file2.txt", "assets/sub/asset1/.git/shouldnt_be_embedded.txt")]
for test in test_cases:
- (srcpath, dstpath1, dstpath2) = test
- make_main_two_files(dstpath1, dstpath2)
+ (srcpath, dstpath1, dstpath2, nonexistingpath) = test
+ make_main_two_files(dstpath1, dstpath2, nonexistingpath)
print srcpath
Popen([PYTHON, EMCC, os.path.join(self.get_dir(), 'main.cpp'), '--preload-file', srcpath, '-o', 'page.html']).communicate()
self.run_browser('page.html', 'You should see |load me right before|.', '/report_result?1')
@@ -12279,9 +12404,10 @@ elif 'browser' in str(sys.argv):
def test_sdl_audio_mix(self):
shutil.copyfile(path_from_root('tests', 'sounds', 'pluck.ogg'), os.path.join(self.get_dir(), 'sound.ogg'))
shutil.copyfile(path_from_root('tests', 'sounds', 'the_entertainer.ogg'), os.path.join(self.get_dir(), 'music.ogg'))
+ shutil.copyfile(path_from_root('tests', 'sounds', 'noise.ogg'), os.path.join(self.get_dir(), 'noise.ogg'))
open(os.path.join(self.get_dir(), 'sdl_audio_mix.c'), 'w').write(self.with_report_result(open(path_from_root('tests', 'sdl_audio_mix.c')).read()))
- Popen([PYTHON, EMCC, '-O2', '--minify', '0', os.path.join(self.get_dir(), 'sdl_audio_mix.c'), '--preload-file', 'sound.ogg', '--preload-file', 'music.ogg', '-o', 'page.html']).communicate()
+ Popen([PYTHON, EMCC, '-O2', '--minify', '0', os.path.join(self.get_dir(), 'sdl_audio_mix.c'), '--preload-file', 'sound.ogg', '--preload-file', 'music.ogg', '--preload-file', 'noise.ogg', '-o', 'page.html']).communicate()
self.run_browser('page.html', '', '/report_result?1')
def test_sdl_audio_quickload(self):
@@ -12298,52 +12424,52 @@ elif 'browser' in str(sys.argv):
def test_sdl_ogl(self):
shutil.copyfile(path_from_root('tests', 'screenshot.png'), os.path.join(self.get_dir(), 'screenshot.png'))
- self.reftest(path_from_root('tests', 'screenshot-gray-purple.png'))
- Popen([PYTHON, EMCC, path_from_root('tests', 'sdl_ogl.c'), '-O2', '--minify', '0', '-o', 'something.html', '--pre-js', 'reftest.js', '--preload-file', 'screenshot.png', '-s', 'GL_TESTING=1']).communicate()
- self.run_browser('something.html', 'You should see an image with gray at the top.', '/report_result?0')
+ self.btest('sdl_ogl.c', reference='screenshot-gray-purple.png',
+ args=['-O2', '--minify', '0', '--preload-file', 'screenshot.png'],
+ message='You should see an image with gray at the top.')
def test_sdl_ogl_defaultmatrixmode(self):
shutil.copyfile(path_from_root('tests', 'screenshot.png'), os.path.join(self.get_dir(), 'screenshot.png'))
- self.reftest(path_from_root('tests', 'screenshot-gray-purple.png'))
- Popen([PYTHON, EMCC, path_from_root('tests', 'sdl_ogl_defaultMatrixMode.c'), '--minify', '0', '-o', 'something.html', '--pre-js', 'reftest.js', '--preload-file', 'screenshot.png', '-s', 'GL_TESTING=1']).communicate()
- self.run_browser('something.html', 'You should see an image with gray at the top.', '/report_result?0')
+ self.btest('sdl_ogl_defaultMatrixMode.c', reference='screenshot-gray-purple.png',
+ args=['--minify', '0', '--preload-file', 'screenshot.png'],
+ message='You should see an image with gray at the top.')
def test_sdl_ogl_p(self):
# Immediate mode with pointers
shutil.copyfile(path_from_root('tests', 'screenshot.png'), os.path.join(self.get_dir(), 'screenshot.png'))
- self.reftest(path_from_root('tests', 'screenshot-gray.png'))
- Popen([PYTHON, EMCC, path_from_root('tests', 'sdl_ogl_p.c'), '-o', 'something.html', '--pre-js', 'reftest.js', '--preload-file', 'screenshot.png', '-s', 'GL_TESTING=1']).communicate()
- self.run_browser('something.html', 'You should see an image with gray at the top.', '/report_result?0')
+ self.btest('sdl_ogl_p.c', reference='screenshot-gray.png',
+ args=['--preload-file', 'screenshot.png'],
+ message='You should see an image with gray at the top.')
def test_sdl_fog_simple(self):
shutil.copyfile(path_from_root('tests', 'screenshot.png'), os.path.join(self.get_dir(), 'screenshot.png'))
- self.reftest(path_from_root('tests', 'screenshot-fog-simple.png'))
- Popen([PYTHON, EMCC, path_from_root('tests', 'sdl_fog_simple.c'), '-O2', '--minify', '0', '-o', 'something.html', '--pre-js', 'reftest.js', '--preload-file', 'screenshot.png', '-s', 'GL_TESTING=1']).communicate()
- self.run_browser('something.html', 'You should see an image with fog.', '/report_result?0')
+ self.btest('sdl_fog_simple.c', reference='screenshot-fog-simple.png',
+ args=['-O2', '--minify', '0', '--preload-file', 'screenshot.png'],
+ message='You should see an image with fog.')
def test_sdl_fog_negative(self):
shutil.copyfile(path_from_root('tests', 'screenshot.png'), os.path.join(self.get_dir(), 'screenshot.png'))
- self.reftest(path_from_root('tests', 'screenshot-fog-negative.png'))
- Popen([PYTHON, EMCC, path_from_root('tests', 'sdl_fog_negative.c'), '-o', 'something.html', '--pre-js', 'reftest.js', '--preload-file', 'screenshot.png', '-s', 'GL_TESTING=1']).communicate()
- self.run_browser('something.html', 'You should see an image with fog.', '/report_result?0')
+ self.btest('sdl_fog_negative.c', reference='screenshot-fog-negative.png',
+ args=['--preload-file', 'screenshot.png'],
+ message='You should see an image with fog.')
def test_sdl_fog_density(self):
shutil.copyfile(path_from_root('tests', 'screenshot.png'), os.path.join(self.get_dir(), 'screenshot.png'))
- self.reftest(path_from_root('tests', 'screenshot-fog-density.png'))
- Popen([PYTHON, EMCC, path_from_root('tests', 'sdl_fog_density.c'), '-o', 'something.html', '--pre-js', 'reftest.js', '--preload-file', 'screenshot.png', '-s', 'GL_TESTING=1']).communicate()
- self.run_browser('something.html', 'You should see an image with fog.', '/report_result?0')
+ self.btest('sdl_fog_density.c', reference='screenshot-fog-density.png',
+ args=['--preload-file', 'screenshot.png'],
+ message='You should see an image with fog.')
def test_sdl_fog_exp2(self):
shutil.copyfile(path_from_root('tests', 'screenshot.png'), os.path.join(self.get_dir(), 'screenshot.png'))
- self.reftest(path_from_root('tests', 'screenshot-fog-exp2.png'))
- Popen([PYTHON, EMCC, path_from_root('tests', 'sdl_fog_exp2.c'), '-o', 'something.html', '--pre-js', 'reftest.js', '--preload-file', 'screenshot.png', '-s', 'GL_TESTING=1']).communicate()
- self.run_browser('something.html', 'You should see an image with fog.', '/report_result?0')
+ self.btest('sdl_fog_exp2.c', reference='screenshot-fog-exp2.png',
+ args=['--preload-file', 'screenshot.png'],
+ message='You should see an image with fog.')
def test_sdl_fog_linear(self):
shutil.copyfile(path_from_root('tests', 'screenshot.png'), os.path.join(self.get_dir(), 'screenshot.png'))
- self.reftest(path_from_root('tests', 'screenshot-fog-linear.png'))
- Popen([PYTHON, EMCC, path_from_root('tests', 'sdl_fog_linear.c'), '-o', 'something.html', '--pre-js', 'reftest.js', '--preload-file', 'screenshot.png', '-s', 'GL_TESTING=1']).communicate()
- self.run_browser('something.html', 'You should see an image with fog.', '/report_result?0')
+ self.btest('sdl_fog_linear.c', reference='screenshot-fog-linear.png',
+ args=['--preload-file', 'screenshot.png'],
+ message='You should see an image with fog.')
def test_openal_playback(self):
shutil.copyfile(path_from_root('tests', 'sounds', 'audio.wav'), os.path.join(self.get_dir(), 'audio.wav'))
@@ -12507,10 +12633,9 @@ elif 'browser' in str(sys.argv):
server.terminate()
def test_glgears(self):
- self.reftest(path_from_root('tests', 'gears.png'))
- Popen([PYTHON, EMCC, path_from_root('tests', 'hello_world_gles.c'), '-o', 'something.html',
- '-DHAVE_BUILTIN_SINCOS', '--pre-js', 'reftest.js', '-s', 'GL_TESTING=1']).communicate()
- self.run_browser('something.html', 'You should see animating gears.', '/report_result?0')
+ self.btest('hello_world_gles.c', reference='gears.png',
+ args=['-DHAVE_BUILTIN_SINCOS'], outfile='something.html',
+ message='You should see animating gears.')
def test_glgears_animation(self):
es2_suffix = ['', '_full', '_full_944']
@@ -12531,12 +12656,11 @@ elif 'browser' in str(sys.argv):
self.btest('full_es2_sdlproc.c', '1', args=['-s', 'GL_TESTING=1', '-DHAVE_BUILTIN_SINCOS', '-s', 'FULL_ES2=1'])
def test_glgears_deriv(self):
- self.reftest(path_from_root('tests', 'gears.png'))
- Popen([PYTHON, EMCC, path_from_root('tests', 'hello_world_gles_deriv.c'), '-o', 'something.html', '-s', 'GL_TESTING=1',
- '-DHAVE_BUILTIN_SINCOS', '--pre-js', 'reftest.js']).communicate()
- self.run_browser('something.html', 'You should see animating gears.', '/report_result?0')
- src = open('something.html').read()
- assert 'gl-matrix' not in src, 'Should not include glMatrix when not needed'
+ self.btest('hello_world_gles_deriv.c', reference='gears.png',
+ args=['-DHAVE_BUILTIN_SINCOS'], outfile='something.html',
+ message='You should see animating gears.')
+ with open('something.html') as f:
+ assert 'gl-matrix' not in f.read(), 'Should not include glMatrix when not needed'
def test_glbook(self):
programs = self.get_library('glbook', [
@@ -12562,26 +12686,28 @@ elif 'browser' in str(sys.argv):
shutil.copyfile(book_path('Chapter_13', 'ParticleSystem', 'smoke.tga'), os.path.join(self.get_dir(), 'smoke.tga'))
args = ['--preload-file', 'smoke.tga', '-O2'] # test optimizations and closure here as well for more coverage
- self.reftest(book_path(basename.replace('.bc', '.png')))
- Popen([PYTHON, EMCC, program, '-o', 'program.html', '--pre-js', 'reftest.js', '-s', 'GL_TESTING=1'] + args).communicate()
- self.run_browser('program.html', '', '/report_result?0')
+ self.btest(program,
+ reference=book_path(basename.replace('.bc', '.png')), args=args)
- def btest(self, filename, expected=None, reference=None, reference_slack=0, args=[]): # TODO: use in all other tests
+ def btest(self, filename, expected=None, reference=None, reference_slack=0,
+ args=[], outfile='test.html', message='.'): # TODO: use in all other tests
+ filepath = path_from_root('tests', filename)
+ temp_filepath = os.path.join(self.get_dir(), os.path.basename(filename))
if not reference:
if '\n' in filename: # if we are provided the source and not a path, use that
src = filename
filename = 'main.cpp'
else:
- src = open(path_from_root('tests', filename)).read()
- open(os.path.join(self.get_dir(), filename), 'w').write(self.with_report_result(src))
+ with open(filepath) as f: src = f.read()
+ with open(temp_filepath, 'w') as f: f.write(self.with_report_result(src))
else:
expected = [str(i) for i in range(0, reference_slack+1)]
- shutil.copyfile(path_from_root('tests', filename), os.path.join(self.get_dir(), os.path.basename(filename)))
+ shutil.copyfile(filepath, temp_filepath)
self.reftest(path_from_root('tests', reference))
args = args + ['--pre-js', 'reftest.js', '-s', 'GL_TESTING=1']
- Popen([PYTHON, EMCC, os.path.join(self.get_dir(), os.path.basename(filename)), '-o', 'test.html'] + args).communicate()
+ Popen([PYTHON, EMCC, temp_filepath, '-o', outfile] + args).communicate()
if type(expected) is str: expected = [expected]
- self.run_browser('test.html', '.', ['/report_result?' + e for e in expected])
+ self.run_browser(outfile, message, ['/report_result?' + e for e in expected])
def test_gles2_emulation(self):
shutil.copyfile(path_from_root('tests', 'glbook', 'Chapter_10', 'MultiTexture', 'basemap.tga'), self.in_dir('basemap.tga'))
@@ -12716,6 +12842,9 @@ elif 'browser' in str(sys.argv):
def test_cube_explosion(self):
self.btest('cube_explosion.c', expected=['667220544', '-1543354600', '-1485258415'])
+ def test_sdl_canvas_blank(self):
+ self.btest('sdl_canvas_blank.c', reference='sdl_canvas_blank.png')
+
def test_sdl_canvas_palette(self):
self.btest('sdl_canvas_palette.c', reference='sdl_canvas_palette.png')
@@ -13185,17 +13314,26 @@ elif 'benchmark' in str(sys.argv):
f.close()
final_filename = os.path.join(dirname, name + '.js')
+ open('hardcode.py', 'w').write('''
+def process(filename):
+ js = open(filename).read()
+ replaced = js.replace("run();", "run(%s.concat(Module[\\"arguments\\"]));")
+ assert js != replaced
+ open(filename, 'w').write(replaced)
+import sys
+process(sys.argv[1])
+''' % str(args[:-1]) # do not hardcode in the last argument, the default arg
+)
+
try_delete(final_filename)
output = Popen([PYTHON, EMCC, filename, #'-O3',
'-O2', '-s', 'DOUBLE_MODE=0', '-s', 'PRECISE_I64_MATH=0',
- '--llvm-lto', '1', '--memory-init-file', '0',
+ '--llvm-lto', '1', '--memory-init-file', '0', '--js-transform', 'python hardcode.py',
'-s', 'TOTAL_MEMORY=128*1024*1024',
'--closure', '1',
'-o', final_filename] + shared_args + emcc_args, stdout=PIPE, stderr=self.stderr_redirect).communicate()
assert os.path.exists(final_filename), 'Failed to compile file: ' + output[0]
- self.hardcode_arguments(final_filename, args)
-
# Run JS
global total_times, tests_done
times = []
@@ -13521,7 +13659,7 @@ elif 'benchmark' in str(sys.argv):
native_args = self.get_library('lua_native', [os.path.join('src', 'lua'), os.path.join('src', 'liblua.a')], make=['make', 'generic'], configure=None, native=True)
self.do_benchmark('lua_' + benchmark, '', expected,
- force_c=True, args=[benchmark + '.lua'], emcc_args=emcc_args, native_args=native_args, native_exec=os.path.join('building', 'lua_native', 'src', 'lua'),
+ force_c=True, args=[benchmark + '.lua', DEFAULT_ARG], emcc_args=emcc_args, native_args=native_args, native_exec=os.path.join('building', 'lua_native', 'src', 'lua'),
output_parser=output_parser, args_processor=args_processor)
def test_zzz_lua_scimark(self):
@@ -13532,21 +13670,7 @@ elif 'benchmark' in str(sys.argv):
def test_zzz_lua_binarytrees(self):
# js version: ['binarytrees.lua', {0: 0, 1: 9.5, 2: 11.99, 3: 12.85, 4: 14.72, 5: 15.82}[arguments[0]]]
- def args_processor(args):
- arg = int(DEFAULT_ARG)
- if arg == 0:
- return args + ['0']
- elif arg == 1:
- return args + ['9.5']
- elif arg == 2:
- return args + ['11.99']
- elif arg == 3:
- return args + ['12.85']
- elif arg == 4:
- return args + ['14.72']
- elif arg == 5:
- return args + ['15.82']
- self.lua('binarytrees', 'long lived tree of depth', args_processor=args_processor)
+ self.lua('binarytrees', 'long lived tree of depth')
def test_zzz_zlib(self):
src = open(path_from_root('tests', 'zlib', 'benchmark.c'), 'r').read()
@@ -13784,7 +13908,7 @@ elif 'sanity' in str(sys.argv):
try:
os.environ['EM_IGNORE_SANITY'] = '1'
- for version, succeed in [(('v0.6.6'), False), (('v0.6.7'), False), (('v0.6.8'), True), (('v0.6.9'), True), (('v0.7.1'), True), (('v0.7.9'), True), (('v0.8.7'), True), (('v0.8.9'), True), ('cheez', False)]:
+ for version, succeed in [('v0.7.9', False), ('v0.8.0', True), ('v0.8.1', True), ('cheez', False)]:
f = open(path_from_root('tests', 'fake', 'nodejs'), 'w')
f.write('#!/bin/sh\n')
f.write('''if [ $1 = "--version" ]; then
@@ -14075,8 +14199,6 @@ else:
raise Exception('Test runner is confused: ' + str(sys.argv))
if __name__ == '__main__':
- sys.argv = [sys.argv[0]] + ['-v'] + sys.argv[1:] # Verbose output by default
-
# Sanity checks
total_engines = len(JS_ENGINES)
@@ -14108,5 +14230,4 @@ if __name__ == '__main__':
# Go
- unittest.main()
-
+ unittest.main(verbosity=2)
diff --git a/tests/sdl_audio_mix.c b/tests/sdl_audio_mix.c
index f72f9c43..a1c0485d 100644
--- a/tests/sdl_audio_mix.c
+++ b/tests/sdl_audio_mix.c
@@ -5,9 +5,11 @@
#include <emscripten.h>
static Mix_Chunk *sound = NULL;
+static Mix_Chunk *noiseLoop = NULL;
static Mix_Music *music = NULL;
static int soundChannel = 0;
+static int noiseLoopChannel = 0;
void one_iter();
void one_iter() {
@@ -19,6 +21,12 @@ void one_iter() {
soundChannel = Mix_PlayChannel(-1, sound, 0);
printf("channel = %d", soundChannel);
assert(soundChannel != -1 && soundChannel != 0);
+
+ noiseLoopChannel = Mix_PlayChannel(-1, noiseLoop, -1);
+ printf("noiseLoopChannel = %d", noiseLoopChannel);
+ assert(noiseLoopChannel != -1 && noiseLoopChannel != 0);
+ // set noiseLoopChannel to half volume
+ Mix_Volume(noiseLoopChannel,MIX_MAX_VOLUME/10);
break;
case 2:
printf("channel %d is playing = %d", soundChannel, Mix_Playing(soundChannel));
@@ -70,9 +78,11 @@ int main(int argc, char **argv) {
sound = Mix_LoadWAV("sound.ogg");
assert(sound);
+ noiseLoop = Mix_LoadWAV("noise.ogg");
+ assert(noiseLoop);
+
music = Mix_LoadMUS("music.ogg");
assert(music);
-
emscripten_set_main_loop(one_iter, 30, 0);
// force a quit
diff --git a/tests/sdl_canvas.c b/tests/sdl_canvas.c
index 97cd1348..10044ff4 100644
--- a/tests/sdl_canvas.c
+++ b/tests/sdl_canvas.c
@@ -38,7 +38,7 @@ int main(int argc, char **argv) {
// fill stuff
SDL_Rect rect = { 200, 200, 175, 125 };
- SDL_FillRect(screen, &rect, 0x2222ffff);
+ SDL_FillRect(screen, &rect, SDL_MapRGBA(screen->format, 0x22, 0x22, 0xff, 0xff));
SDL_Flip(screen);
diff --git a/tests/sdl_canvas_blank.c b/tests/sdl_canvas_blank.c
new file mode 100644
index 00000000..0e7607a6
--- /dev/null
+++ b/tests/sdl_canvas_blank.c
@@ -0,0 +1,17 @@
+#include <stdio.h>
+#include <SDL/SDL.h>
+
+
+int main() {
+ SDL_Init(SDL_INIT_VIDEO);
+ SDL_Surface *screen = SDL_SetVideoMode(256, 256, 32, SDL_SWSURFACE);
+
+ if (SDL_MUSTLOCK(screen)) SDL_LockSurface(screen);
+ if (SDL_MUSTLOCK(screen)) SDL_UnlockSurface(screen);
+ SDL_Flip(screen);
+
+ SDL_Quit();
+
+ return 0;
+}
+
diff --git a/tests/sdl_canvas_blank.png b/tests/sdl_canvas_blank.png
new file mode 100644
index 00000000..dc5a4a26
--- /dev/null
+++ b/tests/sdl_canvas_blank.png
Binary files differ
diff --git a/tests/sdl_canvas_twice.c b/tests/sdl_canvas_twice.c
index 6c6e4802..28a7a01c 100644
--- a/tests/sdl_canvas_twice.c
+++ b/tests/sdl_canvas_twice.c
@@ -8,12 +8,12 @@ int main(int argc, char **argv) {
SDL_Init(SDL_INIT_VIDEO);
SDL_Surface *screen = SDL_SetVideoMode(40, 40, 32, SDL_SWSURFACE);
- SDL_FillRect(screen, NULL, 0xff0000ff);
+ SDL_FillRect(screen, NULL, SDL_MapRGBA(screen->format, 0xff, 0, 0, 0xff));
SDL_LockSurface(screen);
*((int*)screen->pixels + 95) = 0;
SDL_UnlockSurface(screen);
- SDL_FillRect(screen, NULL, 0x00ff00ff); // wipe out previous pixel and fill
+ SDL_FillRect(screen, NULL, SDL_MapRGBA(screen->format, 0, 0xff, 0, 0xff)); // wipe out previous pixel and fill
SDL_LockSurface(screen);
*((int*)screen->pixels + 205) = 0;
SDL_UnlockSurface(screen);
diff --git a/tests/sdl_image_prepare_data.c b/tests/sdl_image_prepare_data.c
index 87e33399..d45a2e60 100644
--- a/tests/sdl_image_prepare_data.c
+++ b/tests/sdl_image_prepare_data.c
@@ -1,4 +1,6 @@
#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
#include <SDL/SDL.h>
#include <SDL/SDL_image.h>
#include <assert.h>
@@ -43,7 +45,7 @@ void ready(void *arg, const char *fileName) {
testImage(seenName);
- free(seenName); // As the API docs say, we are responsible for freeing the 'fake' names we are given
+ free((void*)seenName); // As the API docs say, we are responsible for freeing the 'fake' names we are given
SDL_Flip(screen);
}
diff --git a/tests/sdl_maprgba.c b/tests/sdl_maprgba.c
index c87c7524..4b5c0026 100644
--- a/tests/sdl_maprgba.c
+++ b/tests/sdl_maprgba.c
@@ -1,6 +1,5 @@
#include <stdio.h>
#include <SDL/SDL.h>
-#include <emscripten.h>
int main() {
Uint32 c;
diff --git a/tests/sounds/noise.ogg b/tests/sounds/noise.ogg
new file mode 100644
index 00000000..c53d49a7
--- /dev/null
+++ b/tests/sounds/noise.ogg
Binary files differ
diff --git a/tools/file_packager.py b/tools/file_packager.py
index 1443d165..cc030f59 100644
--- a/tools/file_packager.py
+++ b/tools/file_packager.py
@@ -39,7 +39,7 @@ TODO: You can also provide .crn files yourself, pre-crunched. With this o
to dds files in the browser, exactly the same as if this tool compressed them.
'''
-import os, sys, shutil, random, uuid
+import os, sys, shutil, random, uuid, ctypes
import shared
from shared import Compression, execute, suffix, unsuffixed
@@ -50,6 +50,8 @@ if len(sys.argv) == 1:
See the source for more details.'''
sys.exit(0)
+DEBUG = os.environ.get('EMCC_DEBUG')
+
data_target = sys.argv[1]
IMAGE_SUFFIXES = ('.jpg', '.png', '.bmp')
@@ -150,6 +152,32 @@ function assert(check, msg) {
}
'''
+# Win32 code to test whether the given file has the hidden property set.
+def has_hidden_attribute(filepath):
+ if sys.platform != 'win32':
+ return False
+
+ try:
+ attrs = ctypes.windll.kernel32.GetFileAttributesW(unicode(filepath))
+ assert attrs != -1
+ result = bool(attrs & 2)
+ except (AttributeError, AssertionError):
+ result = False
+ return result
+
+# The packager should never preload/embed any directories that have a component starting with '.' in them,
+# or if the file is hidden (Win32). Note that this filter ONLY applies to directories. Explicitly specified single files
+# are always preloaded/embedded, even if they start with a '.'.
+def should_ignore(filename):
+ if has_hidden_attribute(filename):
+ return True
+
+ components = filename.replace('\\\\', '/').replace('\\', '/').split('/')
+ for c in components:
+ if c.startswith('.') and c != '.' and c != '..':
+ return True
+ return False
+
# Expand directories into individual files
def add(arg, dirname, names):
# rootpathsrc: The path name of the root directory on the local FS we are adding to emscripten virtual FS.
@@ -158,8 +186,12 @@ def add(arg, dirname, names):
for name in names:
fullname = os.path.join(dirname, name)
if not os.path.isdir(fullname):
- dstpath = os.path.join(rootpathdst, os.path.relpath(fullname, rootpathsrc)) # Convert source filename relative to root directory of target FS.
- data_files.append({ 'srcpath': fullname, 'dstpath': dstpath, 'mode': mode })
+ if should_ignore(fullname):
+ if DEBUG:
+ print >> sys.stderr, 'Skipping hidden file "' + fullname + '" from inclusion in the emscripten virtual file system.'
+ else:
+ dstpath = os.path.join(rootpathdst, os.path.relpath(fullname, rootpathsrc)) # Convert source filename relative to root directory of target FS.
+ data_files.append({ 'srcpath': fullname, 'dstpath': dstpath, 'mode': mode })
for file_ in data_files:
if os.path.isdir(file_['srcpath']):
@@ -171,6 +203,8 @@ for file_ in data_files:
if file_['dstpath'].endswith('/'): # If user has submitted a directory name as the destination but omitted the destination filename, use the filename from source file
file_['dstpath'] = file_['dstpath'] + os.path.basename(file_['srcpath'])
if file_['dstpath'].startswith('./'): file_['dstpath'] = file_['dstpath'][2:] # remove redundant ./ prefix
+ if DEBUG:
+ print >> sys.stderr, 'Packaging file "' + file_['srcpath'] + '" to VFS in path "' + file_['dstpath'] + '".'
# Remove duplicates (can occur naively, for example preload dir/, preload dir/subdir/)
seen = {}
@@ -202,7 +236,7 @@ if crunch:
function requestDecrunch(filename, data, callback) {
decrunchWorker.postMessage({
filename: filename,
- data: data,
+ data: new Uint8Array(data),
callbackID: decrunchCallbacks.length
});
decrunchCallbacks.push(callback);
diff --git a/tools/js-optimizer.js b/tools/js-optimizer.js
index 07317e0a..b02ae3cc 100644
--- a/tools/js-optimizer.js
+++ b/tools/js-optimizer.js
@@ -429,19 +429,47 @@ function simplifyExpressionsPre(ast) {
// 'useful' mathops already |0 anyhow.
function simplifyBitops(ast) {
- var SAFE_BINARY_OPS = set('+', '-', '*'); // division is unsafe as it creates non-ints in JS; mod is unsafe as signs matter so we can't remove |0's
+ var SAFE_BINARY_OPS;
+ if (asm) {
+ SAFE_BINARY_OPS = set('+', '-'); // division is unsafe as it creates non-ints in JS; mod is unsafe as signs matter so we can't remove |0's; mul does not nest with +,- in asm
+ } else {
+ SAFE_BINARY_OPS = set('+', '-', '*');
+ }
+ var COERCION_REQUIRING_OPS = set('sub', 'unary-prefix'); // ops that in asm must be coerced right away
+ var COERCION_REQUIRING_BINARIES = set('*', '/', '%'); // binary ops that in asm must be coerced
var ZERO = ['num', 0];
- var rerun = true;
- while (rerun) {
- rerun = false;
- traverse(ast, function process(node, type, stack) {
- if (type == 'binary' && node[1] == '|') {
- if (node[2][0] == 'num' && node[3][0] == 'num') {
- return ['num', node[2][1] | node[3][1]];
- } else if (jsonCompare(node[2], ZERO) || jsonCompare(node[3], ZERO)) {
+
+ function removeMultipleOrZero() {
+ var rerun = true;
+ while (rerun) {
+ rerun = false;
+ traverse(ast, function process(node, type, stack) {
+ if (type == 'binary' && node[1] == '|') {
+ if (node[2][0] == 'num' && node[3][0] == 'num') {
+ return ['num', node[2][1] | node[3][1]];
+ }
+ var go = false;
+ if (jsonCompare(node[2], ZERO)) {
+ // canonicalize order
+ var temp = node[3];
+ node[3] = node[2];
+ node[2] = temp;
+ go = true;
+ } else if (jsonCompare(node[3], ZERO)) {
+ go = true;
+ }
+ if (!go) {
+ stack.push(1);
+ return;
+ }
// We might be able to remove this correction
for (var i = stack.length-1; i >= 0; i--) {
- if (stack[i] == 1) {
+ if (stack[i] >= 1) {
+ if (asm) {
+ if (stack[stack.length-1] < 2 && node[2][0] == 'call') break; // we can only remove multiple |0s on these
+ if (stack[stack.length-1] < 1 && (node[2][0] in COERCION_REQUIRING_OPS ||
+ (node[2][0] == 'binary' && node[2][1] in COERCION_REQUIRING_BINARIES))) break; // we can remove |0 or >>2
+ }
// we will replace ourselves with the non-zero side. Recursively process that node.
var result = jsonCompare(node[2], ZERO) ? node[3] : node[2], other;
// replace node in-place
@@ -453,23 +481,23 @@ function simplifyExpressionsPre(ast) {
return process(result, result[0], stack);
} else if (stack[i] == -1) {
break; // Too bad, we can't
- } else if (asm) {
- break; // we must keep a coercion right on top of a heap access in asm mode
}
}
+ stack.push(2); // From here on up, no need for this kind of correction, it's done at the top
+ // (Add this at the end, so it is only added if we did not remove it)
+ } else if (type == 'binary' && node[1] in USEFUL_BINARY_OPS) {
+ stack.push(1);
+ } else if ((type == 'binary' && node[1] in SAFE_BINARY_OPS) || type == 'num' || type == 'name') {
+ stack.push(0); // This node is safe in that it does not interfere with this optimization
+ } else {
+ stack.push(-1); // This node is dangerous! Give up if you see this before you see '1'
}
- stack.push(1); // From here on up, no need for this kind of correction, it's done at the top
- // (Add this at the end, so it is only added if we did not remove it)
- } else if (type == 'binary' && node[1] in USEFUL_BINARY_OPS) {
- stack.push(1);
- } else if ((type == 'binary' && node[1] in SAFE_BINARY_OPS) || type == 'num' || type == 'name') {
- stack.push(0); // This node is safe in that it does not interfere with this optimization
- } else {
- stack.push(-1); // This node is dangerous! Give up if you see this before you see '1'
- }
- }, null, []);
+ }, null, []);
+ }
}
+ removeMultipleOrZero();
+
// & and heap-related optimizations
var heapBits, heapUnsigned;
@@ -480,7 +508,7 @@ function simplifyExpressionsPre(ast) {
return true;
}
- var hasTempDoublePtr = false;
+ var hasTempDoublePtr = false, rerunOrZeroPass = false;
traverse(ast, function(node, type) {
if (type == 'name') {
@@ -515,7 +543,6 @@ function simplifyExpressionsPre(ast) {
node[2][0] == 'binary' && node[2][1] == '<<' && node[2][3][0] == 'num' &&
node[2][2][0] == 'sub' && node[2][2][1][0] == 'name') {
// collapse HEAPU?8[..] << 24 >> 24 etc. into HEAP8[..] | 0
- // TODO: run this before | 0 | 0 removal, because we generate | 0
var amount = node[3][1];
var name = node[2][2][1][1];
if (amount == node[2][3][1] && parseHeap(name)) {
@@ -524,6 +551,7 @@ function simplifyExpressionsPre(ast) {
node[1] = '|';
node[2] = node[2][2];
node[3][1] = 0;
+ rerunOrZeroPass = true;
return node;
}
}
@@ -556,6 +584,8 @@ function simplifyExpressionsPre(ast) {
}
});
+ if (rerunOrZeroPass) removeMultipleOrZero();
+
if (asm) {
if (hasTempDoublePtr) {
traverse(ast, function(node, type) {
@@ -707,18 +737,11 @@ function simplifyExpressionsPre(ast) {
}
function asmOpts(fun) {
- // 1. Add final returns when necessary
- // 2. Remove unneeded coercions on function calls that have no targets (eliminator removed it)
+ // Add final returns when necessary
var returnType = null;
traverse(fun, function(node, type) {
if (type == 'return' && node[1]) {
returnType = detectAsmCoercion(node[1]);
- } else if (type == 'stat') {
- var inner = node[1];
- if ((inner[0] == 'binary' && inner[1] in ASSOCIATIVE_BINARIES && inner[2][0] == 'call' && inner[3][0] == 'num') ||
- (inner[0] == 'unary-prefix' && inner[1] == '+' && inner[2][0] == 'call')) {
- node[1] = inner[2];
- }
}
});
// Add a final return if one is missing.
diff --git a/tools/shared.py b/tools/shared.py
index 8a172d9c..c16c9115 100644
--- a/tools/shared.py
+++ b/tools/shared.py
@@ -273,7 +273,7 @@ def check_llvm_version():
except Exception, e:
logging.warning('Could not verify LLVM version: %s' % str(e))
-EXPECTED_NODE_VERSION = (0,6,8)
+EXPECTED_NODE_VERSION = (0,8,0)
def check_node_version():
try:
@@ -295,7 +295,7 @@ def check_node_version():
# we re-check sanity when the settings are changed)
# We also re-check sanity and clear the cache when the version changes
-EMSCRIPTEN_VERSION = '1.4.9'
+EMSCRIPTEN_VERSION = '1.5.0'
def generate_sanity():
return EMSCRIPTEN_VERSION + '|' + get_llvm_target()
@@ -454,9 +454,12 @@ EMSCRIPTEN_TEMP_DIR = configuration.EMSCRIPTEN_TEMP_DIR
DEBUG_CACHE = configuration.DEBUG_CACHE
CANONICAL_TEMP_DIR = configuration.CANONICAL_TEMP_DIR
-level = logging.DEBUG if os.environ.get('EMCC_DEBUG') else logging.INFO
-logging.basicConfig(level=level, format='%(levelname)-8s %(name)s: %(message)s')
-
+logging.basicConfig(format='%(levelname)-8s %(name)s: %(message)s')
+def set_logging():
+ logger = logging.getLogger()
+ logger.setLevel(logging.DEBUG if os.environ.get('EMCC_DEBUG') else logging.INFO)
+set_logging()
+
if not EMSCRIPTEN_TEMP_DIR:
EMSCRIPTEN_TEMP_DIR = tempfile.mkdtemp(prefix='emscripten_temp_', dir=configuration.TEMP_DIR)
def clean_temp():
@@ -1091,7 +1094,7 @@ set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE ONLY)''' % { 'winfix': '' if not WINDOWS e
@staticmethod
def can_build_standalone():
- return not Settings.BUILD_AS_SHARED_LIB and not Settings.LINKABLE
+ return not Settings.BUILD_AS_SHARED_LIB and not Settings.LINKABLE and not Settings.EXPORT_ALL
@staticmethod
def can_use_unsafe_opts():
@@ -1285,6 +1288,9 @@ set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE ONLY)''' % { 'winfix': '' if not WINDOWS e
emcc_debug = os.environ.get('EMCC_DEBUG')
if emcc_debug: del os.environ['EMCC_DEBUG']
+ emcc_optimize_normally = os.environ.get('EMCC_OPTIMIZE_NORMALLY')
+ if emcc_optimize_normally: del os.environ['EMCC_OPTIMIZE_NORMALLY']
+
def make(opt_level):
raw = relooper + '.raw.js'
Building.emcc(os.path.join('relooper', 'Relooper.cpp'), ['-I' + os.path.join('relooper'), '--post-js',
@@ -1315,6 +1321,7 @@ set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE ONLY)''' % { 'winfix': '' if not WINDOWS e
finally:
os.chdir(curr)
if emcc_debug: os.environ['EMCC_DEBUG'] = emcc_debug
+ if emcc_optimize_normally: os.environ['EMCC_OPTIMIZE_NORMALLY'] = emcc_optimize_normally
if not ok:
logging.error('bootstrapping relooper failed. You may need to manually create relooper.js by compiling it, see src/relooper/emscripten')
1/0
diff --git a/tools/test-js-optimizer-asm-pre-output.js b/tools/test-js-optimizer-asm-pre-output.js
index 25d521ab..0e95580f 100644
--- a/tools/test-js-optimizer-asm-pre-output.js
+++ b/tools/test-js-optimizer-asm-pre-output.js
@@ -6,9 +6,19 @@ function a() {
f(8);
HEAP[1024] = 5;
HEAP[1024] = 5;
- whee(12, 13);
- whee(12, 13);
+ whee(12, 13) | 0;
+ +whee(12, 13);
f((g = t(), g + g | 0) | 0);
+ f() | 0;
+ f((h() | 0) + 5 | 0);
+ f(x + y + z | 0);
+ +f();
+ f(+(+h() + 5));
+ $140 = $p_3_i + (-$mantSize_0_i | 0) | 0;
+ f(g() | 0);
+ f(g() | 0 & -1);
+ f((g() | 0) >> 2);
+ $56 = _fcntl() | 0 | 1;
}
function b($this, $__n) {
$this = $this | 0;
@@ -34,7 +44,7 @@ function b($this, $__n) {
$23 = HEAP32[($this + 4 & 16777215) >> 2] | 0;
}
if (($14 - $23 | 0) >>> 0 < $__n >>> 0) {
- __ZNSt3__112basic_stringIcNS_11char_traitsIcEENS_9allocatorIcEEE9__grow_byEjjjjjj($this, $14, ($__n - $14 | 0) + $23 | 0, $23, $23);
+ __ZNSt3__112basic_stringIcNS_11char_traitsIcEENS_9allocatorIcEEE9__grow_byEjjjjjj($this, $14, $__n - $14 + $23 | 0, $23, $23);
$30 = HEAP8[$4 & 16777215] | 0;
} else {
$30 = $13;
@@ -161,4 +171,352 @@ function boxx($this, $aabb, $xf, $childIndex) {
HEAPF32[$51 + 4 >> 2] = $_sroa_0_0_insert_insert$1;
return;
}
+function _main($argc, $argv) {
+ $argc = $argc | 0;
+ $argv = $argv | 0;
+ var $def_i21 = 0, $def_i = 0, $world = 0, $bd = 0, $shape = 0, $shape1 = 0, $bd2 = 0, $result = 0, $6 = 0, $WARMUP_0 = 0, $14 = 0, $15 = 0, $17 = 0, $i_09_i_i = 0, $j_08_i_i = 0, $34 = 0, $j_1_i_i = 0, $38 = 0, $46 = 0, $48 = 0, $50 = 0, $54 = 0, $i_05_i_i_i = 0, $56 = 0, $62 = 0, $_lcssa_i_i_i = 0, $87 = 0, $96 = 0, $97 = 0, $98 = 0, $112 = 0, $115 = 0, $116 = 0, $118 = 0, $121 = 0, $126 = 0, $135 = 0, $137 = 0, $174 = 0, $176 = 0, $177 = 0, $178 = 0, $179 = 0, $180 = 0, $181 = 0, $182 = 0, $183 = 0, $185 = 0, $186 = 0, $188 = 0, $189 = 0, $190 = 0, $191 = 0, $192 = 0, $193 = 0, $194 = 0, $195 = 0, $196 = 0, $i_057 = 0, $x_sroa_0_0_load303656 = +0, $x_sroa_1_4_load313755 = +0, $j_052 = 0, $y_sroa_0_0_load283451 = +0, $y_sroa_1_4_load293550 = +0, $y_sroa_0_0_insert_insert$1 = +0, $205 = 0, $208 = 0, $209 = 0, $213 = 0, $223 = 0, $236 = 0, $i3_042 = 0, $241 = 0, $242 = 0, $243 = 0, $i4_038 = 0, $245 = 0, $260 = +0, $_0 = 0, label = 0, __stackBase__ = 0;
+ __stackBase__ = STACKTOP;
+ STACKTOP = STACKTOP + 103416 | 0;
+ $def_i21 = __stackBase__ | 0;
+ $def_i = __stackBase__ + 32 | 0;
+ $world = __stackBase__ + 64 | 0;
+ $bd = __stackBase__ + 103096 | 0;
+ $shape = __stackBase__ + 103152 | 0;
+ $shape1 = __stackBase__ + 103200 | 0;
+ $bd2 = __stackBase__ + 103352 | 0;
+ $result = __stackBase__ + 103408 | 0;
+ do {
+ if (($argc | 0) > 1) {
+ $6 = HEAP8[HEAP32[$argv + 4 >> 2] | 0] | 0;
+ if (($6 | 0) == 49) {
+ HEAP32[2414] = 35;
+ $WARMUP_0 = 5;
+ break;
+ } else if (($6 | 0) == 50) {
+ HEAP32[2414] = 161;
+ $WARMUP_0 = 32;
+ break;
+ } else if (($6 | 0) == 51) {
+ label = 43;
+ break;
+ } else if (($6 | 0) == 52) {
+ HEAP32[2414] = 2331;
+ $WARMUP_0 = 320;
+ break;
+ } else if (($6 | 0) == 53) {
+ HEAP32[2414] = 5661;
+ $WARMUP_0 = 640;
+ break;
+ } else if (($6 | 0) == 48) {
+ $_0 = 0;
+ STACKTOP = __stackBase__;
+ return $_0 | 0;
+ } else {
+ _printf(3512, (tempInt = STACKTOP, STACKTOP = STACKTOP + 8 | 0, HEAP32[tempInt >> 2] = $6 - 48, tempInt) | 0) | 0;
+ $_0 = -1;
+ STACKTOP = __stackBase__;
+ return $_0 | 0;
+ }
+ } else {
+ label = 43;
+ }
+ } while (0);
+ if ((label | 0) == 43) {
+ HEAP32[2414] = 333;
+ $WARMUP_0 = 64;
+ }
+ $14 = $world | 0;
+ $15 = $world + 8 | 0;
+ HEAP32[$15 >> 2] = 128;
+ HEAP32[$world + 4 >> 2] = 0;
+ $17 = _malloc(1024) | 0;
+ HEAP32[$world >> 2] = $17;
+ _memset($17 | 0, 0, HEAP32[$15 >> 2] << 3 | 0);
+ _memset($world + 12 | 0, 0, 56);
+ $j_08_i_i = 0;
+ $i_09_i_i = 1;
+ while (1) {
+ if (!(($j_08_i_i | 0) < 14)) {
+ label = 49;
+ break;
+ }
+ if (($i_09_i_i | 0) > (HEAP32[9600 + ($j_08_i_i << 2) >> 2] | 0)) {
+ $34 = $j_08_i_i + 1 | 0;
+ HEAP8[$i_09_i_i + 8952 | 0] = $34 & 255;
+ $j_1_i_i = $34;
+ } else {
+ HEAP8[$i_09_i_i + 8952 | 0] = $j_08_i_i & 255;
+ $j_1_i_i = $j_08_i_i;
+ }
+ $38 = $i_09_i_i + 1 | 0;
+ if (($38 | 0) < 641) {
+ $j_08_i_i = $j_1_i_i;
+ $i_09_i_i = $38;
+ } else {
+ break;
+ }
+ }
+ if ((label | 0) == 49) {
+ ___assert_func(3248, 73, 6448, 3360);
+ return 0;
+ }
+ HEAP32[$world + 102468 >> 2] = 0;
+ HEAP32[$world + 102472 >> 2] = 0;
+ HEAP32[$world + 102476 >> 2] = 0;
+ HEAP32[$world + 102864 >> 2] = 0;
+ HEAP32[$world + 102872 >> 2] = -1;
+ $46 = $world + 102884 | 0;
+ HEAP32[$46 >> 2] = 16;
+ HEAP32[$world + 102880 >> 2] = 0;
+ $48 = _malloc(576) | 0;
+ $50 = $world + 102876 | 0;
+ HEAP32[$50 >> 2] = $48;
+ _memset($48 | 0, 0, (HEAP32[$46 >> 2] | 0) * 36 & -1 | 0);
+ $54 = (HEAP32[$46 >> 2] | 0) - 1 | 0;
+ if (($54 | 0) > 0) {
+ $i_05_i_i_i = 0;
+ while (1) {
+ $56 = $i_05_i_i_i + 1 | 0;
+ HEAP32[(HEAP32[$50 >> 2] | 0) + ($i_05_i_i_i * 36 & -1) + 20 >> 2] = $56;
+ HEAP32[(HEAP32[$50 >> 2] | 0) + ($i_05_i_i_i * 36 & -1) + 32 >> 2] = -1;
+ $62 = (HEAP32[$46 >> 2] | 0) - 1 | 0;
+ if (($56 | 0) < ($62 | 0)) {
+ $i_05_i_i_i = $56;
+ } else {
+ $_lcssa_i_i_i = $62;
+ break;
+ }
+ }
+ } else {
+ $_lcssa_i_i_i = $54;
+ }
+ HEAP32[(HEAP32[$50 >> 2] | 0) + ($_lcssa_i_i_i * 36 & -1) + 20 >> 2] = -1;
+ HEAP32[(HEAP32[$50 >> 2] | 0) + (((HEAP32[$46 >> 2] | 0) - 1 | 0) * 36 & -1) + 32 >> 2] = -1;
+ _memset($world + 102888 | 0, 0, 16);
+ HEAP32[$world + 102920 >> 2] = 16;
+ HEAP32[$world + 102924 >> 2] = 0;
+ HEAP32[$world + 102916 >> 2] = _malloc(192) | 0;
+ HEAP32[$world + 102908 >> 2] = 16;
+ HEAP32[$world + 102912 >> 2] = 0;
+ HEAP32[$world + 102904 >> 2] = _malloc(64) | 0;
+ HEAP32[$world + 102932 >> 2] = 0;
+ HEAP32[$world + 102936 >> 2] = 0;
+ HEAP32[$world + 102940 >> 2] = 104;
+ HEAP32[$world + 102944 >> 2] = 96;
+ $87 = $world + 102948 | 0;
+ HEAP32[$world + 102980 >> 2] = 0;
+ HEAP32[$world + 102984 >> 2] = 0;
+ _memset($87 | 0, 0, 20);
+ HEAP8[$world + 102992 | 0] = 1;
+ HEAP8[$world + 102993 | 0] = 1;
+ HEAP8[$world + 102994 | 0] = 0;
+ HEAP8[$world + 102995 | 0] = 1;
+ $96 = $world + 102976 | 0;
+ HEAP8[$96] = 1;
+ $97 = $world + 102968 | 0;
+ HEAP32[$97 >> 2] = 0;
+ HEAP32[$97 + 4 >> 2] = -1054867456;
+ $98 = $world + 102868 | 0;
+ HEAP32[$98 >> 2] = 4;
+ HEAPF32[$world + 102988 >> 2] = +0;
+ HEAP32[$87 >> 2] = $14;
+ _memset($world + 102996 | 0, 0, 32);
+ HEAP8[$96] = 0;
+ HEAP32[$bd + 44 >> 2] = 0;
+ _memset($bd + 4 | 0, 0, 32);
+ HEAP8[$bd + 36 | 0] = 1;
+ HEAP8[$bd + 37 | 0] = 1;
+ HEAP8[$bd + 38 | 0] = 0;
+ HEAP8[$bd + 39 | 0] = 0;
+ HEAP32[$bd >> 2] = 0;
+ HEAP8[$bd + 40 | 0] = 1;
+ HEAPF32[$bd + 48 >> 2] = +1;
+ $112 = __ZN16b2BlockAllocator8AllocateEi($14, 152) | 0;
+ if (($112 | 0) == 0) {
+ $116 = 0;
+ } else {
+ $115 = $112;
+ __ZN6b2BodyC2EPK9b2BodyDefP7b2World($115, $bd, $world);
+ $116 = $115;
+ }
+ HEAP32[$116 + 92 >> 2] = 0;
+ $118 = $world + 102952 | 0;
+ HEAP32[$116 + 96 >> 2] = HEAP32[$118 >> 2];
+ $121 = HEAP32[$118 >> 2] | 0;
+ if (!(($121 | 0) == 0)) {
+ HEAP32[$121 + 92 >> 2] = $116;
+ }
+ HEAP32[$118 >> 2] = $116;
+ $126 = $world + 102960 | 0;
+ HEAP32[$126 >> 2] = (HEAP32[$126 >> 2] | 0) + 1;
+ HEAP32[$shape >> 2] = 8016;
+ HEAP32[$shape + 4 >> 2] = 1;
+ HEAPF32[$shape + 8 >> 2] = +.009999999776482582;
+ _memset($shape + 28 | 0, 0, 18);
+ $135 = $shape + 12 | 0;
+ HEAP32[$135 >> 2] = -1038090240;
+ HEAP32[$135 + 4 >> 2] = 0;
+ $137 = $shape + 20 | 0;
+ HEAP32[$137 >> 2] = 1109393408;
+ HEAP32[$137 + 4 >> 2] = 0;
+ HEAP8[$shape + 44 | 0] = 0;
+ HEAP8[$shape + 45 | 0] = 0;
+ HEAP16[$def_i + 22 >> 1] = 1;
+ HEAP16[$def_i + 24 >> 1] = -1;
+ HEAP16[$def_i + 26 >> 1] = 0;
+ HEAP32[$def_i + 4 >> 2] = 0;
+ HEAPF32[$def_i + 8 >> 2] = +.20000000298023224;
+ HEAPF32[$def_i + 12 >> 2] = +0;
+ HEAP8[$def_i + 20 | 0] = 0;
+ HEAP32[$def_i >> 2] = $shape;
+ HEAPF32[$def_i + 16 >> 2] = +0;
+ __ZN6b2Body13CreateFixtureEPK12b2FixtureDef($116, $def_i);
+ HEAP32[$shape1 >> 2] = 7968;
+ HEAP32[$shape1 + 4 >> 2] = 2;
+ HEAPF32[$shape1 + 8 >> 2] = +.009999999776482582;
+ HEAP32[$shape1 + 148 >> 2] = 4;
+ HEAPF32[$shape1 + 20 >> 2] = +-.5;
+ HEAPF32[$shape1 + 24 >> 2] = +-.5;
+ HEAPF32[$shape1 + 28 >> 2] = +.5;
+ HEAPF32[$shape1 + 32 >> 2] = +-.5;
+ HEAPF32[$shape1 + 36 >> 2] = +.5;
+ HEAPF32[$shape1 + 40 >> 2] = +.5;
+ HEAPF32[$shape1 + 44 >> 2] = +-.5;
+ HEAPF32[$shape1 + 48 >> 2] = +.5;
+ HEAPF32[$shape1 + 84 >> 2] = +0;
+ HEAPF32[$shape1 + 88 >> 2] = +-1;
+ HEAPF32[$shape1 + 92 >> 2] = +1;
+ HEAPF32[$shape1 + 96 >> 2] = +0;
+ HEAPF32[$shape1 + 100 >> 2] = +0;
+ HEAPF32[$shape1 + 104 >> 2] = +1;
+ HEAPF32[$shape1 + 108 >> 2] = +-1;
+ HEAPF32[$shape1 + 112 >> 2] = +0;
+ HEAPF32[$shape1 + 12 >> 2] = +0;
+ HEAPF32[$shape1 + 16 >> 2] = +0;
+ $174 = $bd2 + 44 | 0;
+ $176 = $bd2 + 36 | 0;
+ $177 = $bd2 + 4 | 0;
+ $178 = $bd2 + 37 | 0;
+ $179 = $bd2 + 38 | 0;
+ $180 = $bd2 + 39 | 0;
+ $181 = $bd2 | 0;
+ $182 = $bd2 + 40 | 0;
+ $183 = $bd2 + 48 | 0;
+ $185 = $bd2 + 4 | 0;
+ $186 = $shape1 | 0;
+ $188 = $def_i21 + 22 | 0;
+ $189 = $def_i21 + 24 | 0;
+ $190 = $def_i21 + 26 | 0;
+ $191 = $def_i21 | 0;
+ $192 = $def_i21 + 4 | 0;
+ $193 = $def_i21 + 8 | 0;
+ $194 = $def_i21 + 12 | 0;
+ $195 = $def_i21 + 16 | 0;
+ $196 = $def_i21 + 20 | 0;
+ $x_sroa_1_4_load313755 = +.75;
+ $x_sroa_0_0_load303656 = +-7;
+ $i_057 = 0;
+ L82 : while (1) {
+ $y_sroa_1_4_load293550 = $x_sroa_1_4_load313755;
+ $y_sroa_0_0_load283451 = $x_sroa_0_0_load303656;
+ $j_052 = $i_057;
+ while (1) {
+ HEAP32[$174 >> 2] = 0;
+ _memset($177 | 0, 0, 32);
+ HEAP8[$176] = 1;
+ HEAP8[$178] = 1;
+ HEAP8[$179] = 0;
+ HEAP8[$180] = 0;
+ HEAP8[$182] = 1;
+ HEAPF32[$183 >> 2] = +1;
+ HEAP32[$181 >> 2] = 2;
+ $y_sroa_0_0_insert_insert$1 = +$y_sroa_1_4_load293550;
+ HEAPF32[$185 >> 2] = $y_sroa_0_0_load283451;
+ HEAPF32[$185 + 4 >> 2] = $y_sroa_0_0_insert_insert$1;
+ if (!((HEAP32[$98 >> 2] & 2 | 0) == 0)) {
+ label = 65;
+ break L82;
+ }
+ $205 = __ZN16b2BlockAllocator8AllocateEi($14, 152) | 0;
+ if (($205 | 0) == 0) {
+ $209 = 0;
+ } else {
+ $208 = $205;
+ __ZN6b2BodyC2EPK9b2BodyDefP7b2World($208, $bd2, $world);
+ $209 = $208;
+ }
+ HEAP32[$209 + 92 >> 2] = 0;
+ HEAP32[$209 + 96 >> 2] = HEAP32[$118 >> 2];
+ $213 = HEAP32[$118 >> 2] | 0;
+ if (!(($213 | 0) == 0)) {
+ HEAP32[$213 + 92 >> 2] = $209;
+ }
+ HEAP32[$118 >> 2] = $209;
+ HEAP32[$126 >> 2] = (HEAP32[$126 >> 2] | 0) + 1;
+ HEAP16[$188 >> 1] = 1;
+ HEAP16[$189 >> 1] = -1;
+ HEAP16[$190 >> 1] = 0;
+ HEAP32[$192 >> 2] = 0;
+ HEAPF32[$193 >> 2] = +.20000000298023224;
+ HEAPF32[$194 >> 2] = +0;
+ HEAP8[$196] = 0;
+ HEAP32[$191 >> 2] = $186;
+ HEAPF32[$195 >> 2] = +5;
+ __ZN6b2Body13CreateFixtureEPK12b2FixtureDef($209, $def_i21);
+ $223 = $j_052 + 1 | 0;
+ if (($223 | 0) < 40) {
+ $y_sroa_1_4_load293550 = $y_sroa_1_4_load293550 + +0;
+ $y_sroa_0_0_load283451 = $y_sroa_0_0_load283451 + 1.125;
+ $j_052 = $223;
+ } else {
+ break;
+ }
+ }
+ $236 = $i_057 + 1 | 0;
+ if (($236 | 0) < 40) {
+ $x_sroa_1_4_load313755 = $x_sroa_1_4_load313755 + +1;
+ $x_sroa_0_0_load303656 = $x_sroa_0_0_load303656 + +.5625;
+ $i_057 = $236;
+ } else {
+ $i3_042 = 0;
+ break;
+ }
+ }
+ if ((label | 0) == 65) {
+ ___assert_func(112, 109, 5328, 2520);
+ return 0;
+ }
+ while (1) {
+ __ZN7b2World4StepEfii($world);
+ $i3_042 = $i3_042 + 1 | 0;
+ if (($i3_042 | 0) >= ($WARMUP_0 | 0)) {
+ break;
+ }
+ }
+ $241 = HEAP32[2414] | 0;
+ $242 = _llvm_stacksave() | 0;
+ $243 = STACKTOP;
+ STACKTOP = STACKTOP + ($241 * 4 & -1) | 0;
+ STACKTOP = STACKTOP + 7 >> 3 << 3;
+ if (($241 | 0) > 0) {
+ $i4_038 = 0;
+ while (1) {
+ $245 = _clock() | 0;
+ __ZN7b2World4StepEfii($world);
+ HEAP32[$243 + ($i4_038 << 2) >> 2] = (_clock() | 0) - $245;
+ $i4_038 = $i4_038 + 1 | 0;
+ if (($i4_038 | 0) >= (HEAP32[2414] | 0)) {
+ break;
+ }
+ }
+ }
+ __Z7measurePm($result, $243);
+ $260 = +HEAPF32[$result + 4 >> 2];
+ _printf(3480, (tempInt = STACKTOP, STACKTOP = STACKTOP + 16 | 0, HEAPF64[tempInt >> 3] = +HEAPF32[$result >> 2], HEAPF64[tempInt + 8 >> 3] = $260, tempInt) | 0) | 0;
+ _llvm_stackrestore($242 | 0);
+ __ZN7b2WorldD2Ev($world);
+ $_0 = 0;
+ STACKTOP = __stackBase__;
+ return $_0 | 0;
+}
diff --git a/tools/test-js-optimizer-asm-pre.js b/tools/test-js-optimizer-asm-pre.js
index 38487d2f..4f3ba780 100644
--- a/tools/test-js-optimizer-asm-pre.js
+++ b/tools/test-js-optimizer-asm-pre.js
@@ -9,6 +9,17 @@ function a() {
whee(12, 13) | 0;
+whee(12, 13);
f((g = t(), (g+g)|0)|0);
+ // always coerce function calls in asm
+ f() | 0;
+ f((h() | 0) + 5 | 0);
+ f(((x + y) | 0) + z | 0);
+ +f();
+ f(+(+h() + 5));
+ $140 = $p_3_i + (-$mantSize_0_i | 0) | 0;
+ f(g() | 0 | 0);
+ f(g() | 0 & -1);
+ f((g() | 0) >> 2);
+ $56 = (_fcntl() | 0) | 1;
}
function b($this, $__n) {
$this = $this | 0;
@@ -165,4 +176,352 @@ function boxx($this, $aabb, $xf, $childIndex) {
HEAP32[$51 + 4 >> 2] = $_sroa_0_0_insert_insert$1;
return;
}
-// EMSCRIPTEN_GENERATED_FUNCTIONS: ["a", "b", "rett", "ret2t", "retf", "i32_8", "tempDoublePtr", "boxx"]
+function _main($argc, $argv) {
+ $argc = $argc | 0;
+ $argv = $argv | 0;
+ var $def_i21 = 0, $def_i = 0, $world = 0, $bd = 0, $shape = 0, $shape1 = 0, $bd2 = 0, $result = 0, $6 = 0, $WARMUP_0 = 0, $14 = 0, $15 = 0, $17 = 0, $i_09_i_i = 0, $j_08_i_i = 0, $34 = 0, $j_1_i_i = 0, $38 = 0, $46 = 0, $48 = 0, $50 = 0, $54 = 0, $i_05_i_i_i = 0, $56 = 0, $62 = 0, $_lcssa_i_i_i = 0, $87 = 0, $96 = 0, $97 = 0, $98 = 0, $112 = 0, $115 = 0, $116 = 0, $118 = 0, $121 = 0, $126 = 0, $135 = 0, $137 = 0, $174 = 0, $176 = 0, $177 = 0, $178 = 0, $179 = 0, $180 = 0, $181 = 0, $182 = 0, $183 = 0, $185 = 0, $186 = 0, $188 = 0, $189 = 0, $190 = 0, $191 = 0, $192 = 0, $193 = 0, $194 = 0, $195 = 0, $196 = 0, $i_057 = 0, $x_sroa_0_0_load303656 = +0, $x_sroa_1_4_load313755 = +0, $j_052 = 0, $y_sroa_0_0_load283451 = +0, $y_sroa_1_4_load293550 = +0, $y_sroa_0_0_insert_insert$1 = 0, $205 = 0, $208 = 0, $209 = 0, $213 = 0, $223 = 0, $236 = 0, $i3_042 = 0, $241 = 0, $242 = 0, $243 = 0, $i4_038 = 0, $245 = 0, $260 = +0, $_0 = 0, label = 0, __stackBase__ = 0;
+ __stackBase__ = STACKTOP;
+ STACKTOP = STACKTOP + 103416 | 0;
+ $def_i21 = __stackBase__ | 0;
+ $def_i = __stackBase__ + 32 | 0;
+ $world = __stackBase__ + 64 | 0;
+ $bd = __stackBase__ + 103096 | 0;
+ $shape = __stackBase__ + 103152 | 0;
+ $shape1 = __stackBase__ + 103200 | 0;
+ $bd2 = __stackBase__ + 103352 | 0;
+ $result = __stackBase__ + 103408 | 0;
+ do {
+ if (($argc | 0) > 1) {
+ $6 = (HEAP8[HEAP32[($argv + 4 | 0) >> 2] | 0] | 0) << 24 >> 24;
+ if (($6 | 0 | 0) == (49 | 0)) {
+ HEAP32[9656 >> 2] = 35;
+ $WARMUP_0 = 5;
+ break;
+ } else if (($6 | 0 | 0) == (50 | 0)) {
+ HEAP32[9656 >> 2] = 161;
+ $WARMUP_0 = 32;
+ break;
+ } else if (($6 | 0 | 0) == (51 | 0)) {
+ label = 43;
+ break;
+ } else if (($6 | 0 | 0) == (52 | 0)) {
+ HEAP32[9656 >> 2] = 2331;
+ $WARMUP_0 = 320;
+ break;
+ } else if (($6 | 0 | 0) == (53 | 0)) {
+ HEAP32[9656 >> 2] = 5661;
+ $WARMUP_0 = 640;
+ break;
+ } else if (($6 | 0 | 0) == (48 | 0)) {
+ $_0 = 0;
+ STACKTOP = __stackBase__;
+ return $_0 | 0;
+ } else {
+ _printf(3512 | 0 | 0, (tempInt = STACKTOP, STACKTOP = STACKTOP + 8 | 0, HEAP32[tempInt >> 2] = $6 - 48 | 0, tempInt) | 0) | 0;
+ $_0 = -1;
+ STACKTOP = __stackBase__;
+ return $_0 | 0;
+ }
+ } else {
+ label = 43;
+ }
+ } while (0);
+ if ((label | 0) == 43) {
+ HEAP32[9656 >> 2] = 333;
+ $WARMUP_0 = 64;
+ }
+ $14 = $world | 0;
+ $15 = $world + 8 | 0;
+ HEAP32[$15 >> 2] = 128;
+ HEAP32[($world + 4 | 0) >> 2] = 0;
+ $17 = _malloc(1024) | 0;
+ HEAP32[($world | 0) >> 2] = $17;
+ _memset($17 | 0 | 0, 0 | 0 | 0, (HEAP32[$15 >> 2] | 0) << 3 | 0 | 0);
+ _memset($world + 12 | 0 | 0 | 0, 0 | 0 | 0, 56 | 0 | 0);
+ $j_08_i_i = 0;
+ $i_09_i_i = 1;
+ while (1) {
+ if (!(($j_08_i_i | 0) < 14)) {
+ label = 49;
+ break;
+ }
+ if (($i_09_i_i | 0) > (HEAP32[(9600 + ($j_08_i_i << 2) | 0) >> 2] | 0 | 0)) {
+ $34 = $j_08_i_i + 1 | 0;
+ HEAP8[$i_09_i_i + 8952 | 0] = $34 & 255;
+ $j_1_i_i = $34;
+ } else {
+ HEAP8[$i_09_i_i + 8952 | 0] = $j_08_i_i & 255;
+ $j_1_i_i = $j_08_i_i;
+ }
+ $38 = $i_09_i_i + 1 | 0;
+ if (($38 | 0) < 641) {
+ $j_08_i_i = $j_1_i_i;
+ $i_09_i_i = $38;
+ } else {
+ break;
+ }
+ }
+ if ((label | 0) == 49) {
+ ___assert_func(3248 | 0 | 0, 73 | 0, 6448 | 0 | 0, 3360 | 0 | 0);
+ return 0 | 0;
+ }
+ HEAP32[($world + 102468 | 0) >> 2] = 0;
+ HEAP32[($world + 102472 | 0) >> 2] = 0;
+ HEAP32[($world + 102476 | 0) >> 2] = 0;
+ HEAP32[($world + 102864 | 0) >> 2] = 0;
+ HEAP32[($world + 102872 | 0) >> 2] = -1;
+ $46 = $world + 102884 | 0;
+ HEAP32[$46 >> 2] = 16;
+ HEAP32[($world + 102880 | 0) >> 2] = 0;
+ $48 = _malloc(576) | 0;
+ $50 = $world + 102876 | 0;
+ HEAP32[$50 >> 2] = $48;
+ _memset($48 | 0 | 0, 0 | 0 | 0, (HEAP32[$46 >> 2] | 0) * 36 & -1 | 0 | 0);
+ $54 = (HEAP32[$46 >> 2] | 0) - 1 | 0;
+ if (($54 | 0) > 0) {
+ $i_05_i_i_i = 0;
+ while (1) {
+ $56 = $i_05_i_i_i + 1 | 0;
+ HEAP32[((HEAP32[$50 >> 2] | 0) + ($i_05_i_i_i * 36 & -1) + 20 | 0) >> 2] = $56;
+ HEAP32[((HEAP32[$50 >> 2] | 0) + ($i_05_i_i_i * 36 & -1) + 32 | 0) >> 2] = -1;
+ $62 = (HEAP32[$46 >> 2] | 0) - 1 | 0;
+ if (($56 | 0) < ($62 | 0)) {
+ $i_05_i_i_i = $56;
+ } else {
+ $_lcssa_i_i_i = $62;
+ break;
+ }
+ }
+ } else {
+ $_lcssa_i_i_i = $54;
+ }
+ HEAP32[((HEAP32[$50 >> 2] | 0) + ($_lcssa_i_i_i * 36 & -1) + 20 | 0) >> 2] = -1;
+ HEAP32[((HEAP32[$50 >> 2] | 0) + (((HEAP32[$46 >> 2] | 0) - 1 | 0) * 36 & -1) + 32 | 0) >> 2] = -1;
+ _memset($world + 102888 | 0 | 0 | 0, 0 | 0 | 0, 16 | 0 | 0);
+ HEAP32[($world + 102920 | 0) >> 2] = 16;
+ HEAP32[($world + 102924 | 0) >> 2] = 0;
+ HEAP32[($world + 102916 | 0) >> 2] = _malloc(192) | 0;
+ HEAP32[($world + 102908 | 0) >> 2] = 16;
+ HEAP32[($world + 102912 | 0) >> 2] = 0;
+ HEAP32[($world + 102904 | 0) >> 2] = _malloc(64) | 0;
+ HEAP32[($world + 102932 | 0) >> 2] = 0;
+ HEAP32[($world + 102936 | 0) >> 2] = 0;
+ HEAP32[($world + 102940 | 0) >> 2] = 104;
+ HEAP32[($world + 102944 | 0) >> 2] = 96;
+ $87 = $world + 102948 | 0;
+ HEAP32[($world + 102980 | 0) >> 2] = 0;
+ HEAP32[($world + 102984 | 0) >> 2] = 0;
+ _memset($87 | 0 | 0, 0 | 0 | 0, 20 | 0 | 0);
+ HEAP8[$world + 102992 | 0] = 1;
+ HEAP8[$world + 102993 | 0] = 1;
+ HEAP8[$world + 102994 | 0] = 0;
+ HEAP8[$world + 102995 | 0] = 1;
+ $96 = $world + 102976 | 0;
+ HEAP8[$96] = 1;
+ $97 = $world + 102968 | 0;
+ HEAP32[($97 | 0) >> 2] = 0;
+ HEAP32[($97 + 4 | 0) >> 2] = -1054867456;
+ $98 = $world + 102868 | 0;
+ HEAP32[$98 >> 2] = 4;
+ HEAPF32[($world + 102988 | 0) >> 2] = +0;
+ HEAP32[$87 >> 2] = $14;
+ _memset($world + 102996 | 0 | 0 | 0, 0 | 0 | 0, 32 | 0 | 0);
+ HEAP8[$96] = 0;
+ HEAP32[($bd + 44 | 0) >> 2] = 0;
+ _memset($bd + 4 | 0 | 0 | 0, 0 | 0 | 0, 32 | 0 | 0);
+ HEAP8[$bd + 36 | 0] = 1;
+ HEAP8[$bd + 37 | 0] = 1;
+ HEAP8[$bd + 38 | 0] = 0;
+ HEAP8[$bd + 39 | 0] = 0;
+ HEAP32[($bd | 0) >> 2] = 0;
+ HEAP8[$bd + 40 | 0] = 1;
+ HEAPF32[($bd + 48 | 0) >> 2] = +1;
+ $112 = __ZN16b2BlockAllocator8AllocateEi($14, 152) | 0;
+ if (($112 | 0) == 0) {
+ $116 = 0;
+ } else {
+ $115 = $112;
+ __ZN6b2BodyC2EPK9b2BodyDefP7b2World($115, $bd, $world);
+ $116 = $115;
+ }
+ HEAP32[($116 + 92 | 0) >> 2] = 0;
+ $118 = $world + 102952 | 0;
+ HEAP32[($116 + 96 | 0) >> 2] = HEAP32[$118 >> 2] | 0;
+ $121 = HEAP32[$118 >> 2] | 0;
+ if (!(($121 | 0) == 0)) {
+ HEAP32[($121 + 92 | 0) >> 2] = $116;
+ }
+ HEAP32[$118 >> 2] = $116;
+ $126 = $world + 102960 | 0;
+ HEAP32[$126 >> 2] = (HEAP32[$126 >> 2] | 0) + 1 | 0;
+ HEAP32[($shape | 0) >> 2] = 8016 | 0;
+ HEAP32[($shape + 4 | 0) >> 2] = 1;
+ HEAPF32[($shape + 8 | 0) >> 2] = +.009999999776482582;
+ _memset($shape + 28 | 0 | 0 | 0, 0 | 0 | 0, 18 | 0 | 0);
+ $135 = $shape + 12 | 0;
+ HEAP32[($135 | 0) >> 2] = -1038090240;
+ HEAP32[($135 + 4 | 0) >> 2] = 0;
+ $137 = $shape + 20 | 0;
+ HEAP32[($137 | 0) >> 2] = 1109393408;
+ HEAP32[($137 + 4 | 0) >> 2] = 0;
+ HEAP8[$shape + 44 | 0] = 0;
+ HEAP8[$shape + 45 | 0] = 0;
+ HEAP16[($def_i + 22 | 0) >> 1] = 1;
+ HEAP16[($def_i + 24 | 0) >> 1] = -1;
+ HEAP16[($def_i + 26 | 0) >> 1] = 0;
+ HEAP32[($def_i + 4 | 0) >> 2] = 0;
+ HEAPF32[($def_i + 8 | 0) >> 2] = +.20000000298023224;
+ HEAPF32[($def_i + 12 | 0) >> 2] = +0;
+ HEAP8[$def_i + 20 | 0] = 0;
+ HEAP32[($def_i | 0) >> 2] = $shape | 0;
+ HEAPF32[($def_i + 16 | 0) >> 2] = +0;
+ __ZN6b2Body13CreateFixtureEPK12b2FixtureDef($116, $def_i);
+ HEAP32[($shape1 | 0) >> 2] = 7968 | 0;
+ HEAP32[($shape1 + 4 | 0) >> 2] = 2;
+ HEAPF32[($shape1 + 8 | 0) >> 2] = +.009999999776482582;
+ HEAP32[($shape1 + 148 | 0) >> 2] = 4;
+ HEAPF32[($shape1 + 20 | 0) >> 2] = +-.5;
+ HEAPF32[($shape1 + 24 | 0) >> 2] = +-.5;
+ HEAPF32[($shape1 + 28 | 0) >> 2] = +.5;
+ HEAPF32[($shape1 + 32 | 0) >> 2] = +-.5;
+ HEAPF32[($shape1 + 36 | 0) >> 2] = +.5;
+ HEAPF32[($shape1 + 40 | 0) >> 2] = +.5;
+ HEAPF32[($shape1 + 44 | 0) >> 2] = +-.5;
+ HEAPF32[($shape1 + 48 | 0) >> 2] = +.5;
+ HEAPF32[($shape1 + 84 | 0) >> 2] = +0;
+ HEAPF32[($shape1 + 88 | 0) >> 2] = +-1;
+ HEAPF32[($shape1 + 92 | 0) >> 2] = +1;
+ HEAPF32[($shape1 + 96 | 0) >> 2] = +0;
+ HEAPF32[($shape1 + 100 | 0) >> 2] = +0;
+ HEAPF32[($shape1 + 104 | 0) >> 2] = +1;
+ HEAPF32[($shape1 + 108 | 0) >> 2] = +-1;
+ HEAPF32[($shape1 + 112 | 0) >> 2] = +0;
+ HEAPF32[($shape1 + 12 | 0) >> 2] = +0;
+ HEAPF32[($shape1 + 16 | 0) >> 2] = +0;
+ $174 = $bd2 + 44 | 0;
+ $176 = $bd2 + 36 | 0;
+ $177 = $bd2 + 4 | 0;
+ $178 = $bd2 + 37 | 0;
+ $179 = $bd2 + 38 | 0;
+ $180 = $bd2 + 39 | 0;
+ $181 = $bd2 | 0;
+ $182 = $bd2 + 40 | 0;
+ $183 = $bd2 + 48 | 0;
+ $185 = $bd2 + 4 | 0;
+ $186 = $shape1 | 0;
+ $188 = $def_i21 + 22 | 0;
+ $189 = $def_i21 + 24 | 0;
+ $190 = $def_i21 + 26 | 0;
+ $191 = $def_i21 | 0;
+ $192 = $def_i21 + 4 | 0;
+ $193 = $def_i21 + 8 | 0;
+ $194 = $def_i21 + 12 | 0;
+ $195 = $def_i21 + 16 | 0;
+ $196 = $def_i21 + 20 | 0;
+ $x_sroa_1_4_load313755 = +.75;
+ $x_sroa_0_0_load303656 = +-7;
+ $i_057 = 0;
+ L82 : while (1) {
+ $y_sroa_1_4_load293550 = $x_sroa_1_4_load313755;
+ $y_sroa_0_0_load283451 = $x_sroa_0_0_load303656;
+ $j_052 = $i_057;
+ while (1) {
+ HEAP32[$174 >> 2] = 0;
+ _memset($177 | 0 | 0, 0 | 0 | 0, 32 | 0 | 0);
+ HEAP8[$176] = 1;
+ HEAP8[$178] = 1;
+ HEAP8[$179] = 0;
+ HEAP8[$180] = 0;
+ HEAP8[$182] = 1;
+ HEAPF32[$183 >> 2] = +1;
+ HEAP32[$181 >> 2] = 2;
+ $y_sroa_0_0_insert_insert$1 = (HEAPF32[tempDoublePtr >> 2] = $y_sroa_1_4_load293550, HEAP32[tempDoublePtr >> 2] | 0) | 0;
+ HEAP32[($185 | 0) >> 2] = 0 | (HEAPF32[tempDoublePtr >> 2] = $y_sroa_0_0_load283451, HEAP32[tempDoublePtr >> 2] | 0);
+ HEAP32[($185 + 4 | 0) >> 2] = $y_sroa_0_0_insert_insert$1;
+ if (!(((HEAP32[$98 >> 2] | 0) & 2 | 0) == 0)) {
+ label = 65;
+ break L82;
+ }
+ $205 = __ZN16b2BlockAllocator8AllocateEi($14, 152) | 0;
+ if (($205 | 0) == 0) {
+ $209 = 0;
+ } else {
+ $208 = $205;
+ __ZN6b2BodyC2EPK9b2BodyDefP7b2World($208, $bd2, $world);
+ $209 = $208;
+ }
+ HEAP32[($209 + 92 | 0) >> 2] = 0;
+ HEAP32[($209 + 96 | 0) >> 2] = HEAP32[$118 >> 2] | 0;
+ $213 = HEAP32[$118 >> 2] | 0;
+ if (!(($213 | 0) == 0)) {
+ HEAP32[($213 + 92 | 0) >> 2] = $209;
+ }
+ HEAP32[$118 >> 2] = $209;
+ HEAP32[$126 >> 2] = (HEAP32[$126 >> 2] | 0) + 1 | 0;
+ HEAP16[$188 >> 1] = 1;
+ HEAP16[$189 >> 1] = -1;
+ HEAP16[$190 >> 1] = 0;
+ HEAP32[$192 >> 2] = 0;
+ HEAPF32[$193 >> 2] = +.20000000298023224;
+ HEAPF32[$194 >> 2] = +0;
+ HEAP8[$196] = 0;
+ HEAP32[$191 >> 2] = $186;
+ HEAPF32[$195 >> 2] = +5;
+ __ZN6b2Body13CreateFixtureEPK12b2FixtureDef($209, $def_i21);
+ $223 = $j_052 + 1 | 0;
+ if (($223 | 0) < 40) {
+ $y_sroa_1_4_load293550 = $y_sroa_1_4_load293550 + +0;
+ $y_sroa_0_0_load283451 = $y_sroa_0_0_load283451 + 1.125;
+ $j_052 = $223;
+ } else {
+ break;
+ }
+ }
+ $236 = $i_057 + 1 | 0;
+ if (($236 | 0) < 40) {
+ $x_sroa_1_4_load313755 = $x_sroa_1_4_load313755 + +1;
+ $x_sroa_0_0_load303656 = $x_sroa_0_0_load303656 + +.5625;
+ $i_057 = $236;
+ } else {
+ $i3_042 = 0;
+ break;
+ }
+ }
+ if ((label | 0) == 65) {
+ ___assert_func(112 | 0 | 0, 109 | 0, 5328 | 0 | 0, 2520 | 0 | 0);
+ return 0 | 0;
+ }
+ while (1) {
+ __ZN7b2World4StepEfii($world);
+ $i3_042 = $i3_042 + 1 | 0;
+ if (($i3_042 | 0) >= ($WARMUP_0 | 0)) {
+ break;
+ }
+ }
+ $241 = HEAP32[9656 >> 2] | 0;
+ $242 = _llvm_stacksave() | 0;
+ $243 = STACKTOP;
+ STACKTOP = STACKTOP + ($241 * 4 & -1) | 0;
+ STACKTOP = STACKTOP + 7 >> 3 << 3;
+ if (($241 | 0) > 0) {
+ $i4_038 = 0;
+ while (1) {
+ $245 = _clock() | 0;
+ __ZN7b2World4StepEfii($world);
+ HEAP32[($243 + ($i4_038 << 2) | 0) >> 2] = (_clock() | 0) - $245 | 0;
+ $i4_038 = $i4_038 + 1 | 0;
+ if (($i4_038 | 0) >= (HEAP32[9656 >> 2] | 0 | 0)) {
+ break;
+ }
+ }
+ }
+ __Z7measurePm($result, $243);
+ $260 = +HEAPF32[($result + 4 | 0) >> 2];
+ _printf(3480 | 0 | 0, (tempInt = STACKTOP, STACKTOP = STACKTOP + 16 | 0, HEAPF64[tempInt >> 3] = +HEAPF32[($result | 0) >> 2], HEAPF64[tempInt + 8 >> 3] = $260, tempInt) | 0) | 0;
+ _llvm_stackrestore($242 | 0);
+ __ZN7b2WorldD2Ev($world);
+ $_0 = 0;
+ STACKTOP = __stackBase__;
+ return $_0 | 0;
+}
+// EMSCRIPTEN_GENERATED_FUNCTIONS: ["a", "b", "rett", "ret2t", "retf", "i32_8", "tempDoublePtr", "boxx", "_main"]