aboutsummaryrefslogtreecommitdiff
path: root/tests
diff options
context:
space:
mode:
Diffstat (limited to 'tests')
-rw-r--r--tests/cases/storebigfloat.ll17
-rw-r--r--tests/emscripten_get_now.cpp6
-rw-r--r--tests/lua/Makefile3
-rw-r--r--tests/lua/src/Makefile3
-rwxr-xr-xtests/runner.py2
-rw-r--r--tests/sdl_joystick.c124
-rw-r--r--tests/test_benchmark.py14
-rw-r--r--tests/test_browser.py76
-rw-r--r--tests/test_core.py53
9 files changed, 283 insertions, 15 deletions
diff --git a/tests/cases/storebigfloat.ll b/tests/cases/storebigfloat.ll
new file mode 100644
index 00000000..c9995835
--- /dev/null
+++ b/tests/cases/storebigfloat.ll
@@ -0,0 +1,17 @@
+
+@.str = private unnamed_addr constant [15 x i8] c"hello, world!\0A\00", align 1 ; [#uses=1 type=[15 x i8]*]
+
+; [#uses=0]
+define i32 @main() {
+entry:
+ %retval = alloca i32, align 4 ; [#uses=1 type=i32*]
+ %f = alloca float, align 4
+ store float 1.000000e+10, float* %f, align 4
+ store i32 0, i32* %retval
+ %call = call i32 (i8*, ...)* @printf(i8* getelementptr inbounds ([15 x i8]* @.str, i32 0, i32 0)) ; [#uses=0 type=i32]
+ ret i32 1
+}
+
+; [#uses=1]
+declare i32 @printf(i8*, ...)
+
diff --git a/tests/emscripten_get_now.cpp b/tests/emscripten_get_now.cpp
index 17aa7d32..5ededb23 100644
--- a/tests/emscripten_get_now.cpp
+++ b/tests/emscripten_get_now.cpp
@@ -14,10 +14,10 @@ int main() {
// b) Values returned by emscripten_get_now() are strictly nondecreasing.
// c) emscripten_get_now() is able to return sub-millisecond precision timer values.
bool detected_good_timer_precision = false;
- float smallest_delta = 0.f;
+ double smallest_delta = 0.f;
for(int x = 0; x < 1000; ++x) { // Have several attempts to find a good small delta, i.e. give time to JS engine to warm up the code and so on.
- float t = emscripten_get_now();
- float t2 = emscripten_get_now();
+ double t = emscripten_get_now();
+ double t2 = emscripten_get_now();
for(int i = 0; i < 100 && t == t2; ++i) {
t2 = emscripten_get_now();
}
diff --git a/tests/lua/Makefile b/tests/lua/Makefile
index bd9515fd..9f0a2edd 100644
--- a/tests/lua/Makefile
+++ b/tests/lua/Makefile
@@ -51,8 +51,9 @@ R= $V.1
# Targets start here.
all: $(PLAT)
+# XXX Emscripten Added quotes to $(MAKE) to properly call make when the path contains spaces
$(PLATS) clean:
- cd src && $(MAKE) $@
+ cd src && "$(MAKE)" $@
test: dummy
src/lua -v
diff --git a/tests/lua/src/Makefile b/tests/lua/src/Makefile
index 401e7367..a9cf0911 100644
--- a/tests/lua/src/Makefile
+++ b/tests/lua/src/Makefile
@@ -59,8 +59,9 @@ o: $(ALL_O)
a: $(ALL_A)
+# XXX EMSCRIPTEN: add AR_ARGS
$(LUA_A): $(BASE_O)
- $(AR) $(AR_ARGS) $@ $(BASE_O) # XXX EMSCRIPTEN: add AR_ARGS
+ $(AR) $(AR_ARGS) $@ $(BASE_O)
$(RANLIB) $@
$(LUA_T): $(LUA_O) $(LUA_A)
diff --git a/tests/runner.py b/tests/runner.py
index 867f7113..8c4a9abf 100755
--- a/tests/runner.py
+++ b/tests/runner.py
@@ -36,7 +36,7 @@ except:
# Core test runner class, shared between normal tests and benchmarks
checked_sanity = False
-test_modes = ['default', 'o1', 'o2', 'asm1', 'asm2', 'asm2g', 'asm2x86', 's_0_0', 's_0_1']
+test_modes = ['default', 'o1', 'o2', 'asm1', 'asm2', 'asm2f', 'asm2g', 'asm2x86', 's_0_0', 's_0_1']
test_index = 0
class RunnerCore(unittest.TestCase):
diff --git a/tests/sdl_joystick.c b/tests/sdl_joystick.c
new file mode 100644
index 00000000..50802c31
--- /dev/null
+++ b/tests/sdl_joystick.c
@@ -0,0 +1,124 @@
+#include <stdio.h>
+#include <SDL/SDL.h>
+#include <SDL/SDL_ttf.h>
+#include <assert.h>
+#include <string.h>
+#include <emscripten.h>
+
+int result = 1;
+
+void assertJoystickEvent(int expectedGamepad, int expectedType, int expectedIndex, int expectedValue) {
+ SDL_Event event;
+ while(1) {
+ // Loop ends either when assertion fails (we run out of events), or we find
+ // the event we're looking for.
+ assert(SDL_PollEvent(&event) == 1);
+ if (event.type != expectedType) {
+ continue;
+ }
+ switch(event.type) {
+ case SDL_JOYAXISMOTION: {
+ assert(event.jaxis.which == expectedGamepad);
+ assert(event.jaxis.axis == expectedIndex);
+ assert(event.jaxis.value == expectedValue);
+ break;
+ }
+ case SDL_JOYBUTTONUP: case SDL_JOYBUTTONDOWN: {
+ assert(event.jbutton.which == expectedGamepad);
+ assert(event.jbutton.button == expectedIndex);
+ assert(event.jbutton.state == expectedValue);
+ break;
+ }
+ }
+ // Break out of while loop.
+ break;
+ }
+}
+
+void assertNoJoystickEvent() {
+ SDL_Event event;
+ while(SDL_PollEvent(&event)) {
+ switch(event.type) {
+ case SDL_JOYBUTTONDOWN: case SDL_JOYBUTTONUP: case SDL_JOYAXISMOTION: {
+ // Fail.
+ assert(0);
+ }
+ }
+ }
+}
+
+void main_2(void* arg);
+
+int main() {
+ SDL_Init(SDL_INIT_VIDEO | SDL_INIT_JOYSTICK);
+ SDL_Surface *screen = SDL_SetVideoMode(600, 450, 32, SDL_HWSURFACE);
+ emscripten_async_call(main_2, NULL, 3000); // avoid startup delays and intermittent errors
+ return 0;
+}
+
+void main_2(void* arg) {
+ // TODO: At the moment, we only support joystick support through polling.
+ emscripten_run_script("window.addNewGamepad('Pad Thai', 4, 16)");
+ emscripten_run_script("window.addNewGamepad('Pad Kee Mao', 0, 4)");
+ // Check that the joysticks exist properly.
+ assert(SDL_NumJoysticks() == 2);
+ assert(!SDL_JoystickOpened(0));
+ assert(!SDL_JoystickOpened(1));
+ SDL_Joystick* pad1 = SDL_JoystickOpen(0);
+ assert(SDL_JoystickOpened(0));
+ assert(SDL_JoystickIndex(pad1) == 0);
+ assert(strncmp(SDL_JoystickName(0), "Pad Thai", 9) == 0);
+ assert(strncmp(SDL_JoystickName(1), "Pad Kee Mao", 12) == 0);
+ assert(SDL_JoystickNumAxes(pad1) == 4);
+ assert(SDL_JoystickNumButtons(pad1) == 16);
+
+ // Button events.
+ emscripten_run_script("window.simulateGamepadButtonDown(0, 1)");
+ // We didn't tell SDL to automatically update this joystick's state.
+ assertNoJoystickEvent();
+ SDL_JoystickUpdate();
+ assertJoystickEvent(0, SDL_JOYBUTTONDOWN, 1, SDL_PRESSED);
+ assert(SDL_JoystickGetButton(pad1, 1) == 1);
+ // Enable automatic updates.
+ SDL_JoystickEventState(SDL_ENABLE);
+ assert(SDL_JoystickEventState(SDL_QUERY) == SDL_ENABLE);
+ emscripten_run_script("window.simulateGamepadButtonUp(0, 1)");
+ assertJoystickEvent(0, SDL_JOYBUTTONUP, 1, SDL_RELEASED);
+ assert(SDL_JoystickGetButton(pad1, 1) == 0);
+ // No button change: Should not result in a new event.
+ emscripten_run_script("window.simulateGamepadButtonUp(0, 1)");
+ assertNoJoystickEvent();
+ // Joystick 1 is not opened; should not result in a new event.
+ emscripten_run_script("window.simulateGamepadButtonDown(1, 1)");
+ assertNoJoystickEvent();
+
+ // Joystick wiggling
+ emscripten_run_script("window.simulateAxisMotion(0, 0, 1)");
+ assertJoystickEvent(0, SDL_JOYAXISMOTION, 0, 32767);
+ assert(SDL_JoystickGetAxis(pad1, 0) == 32767);
+ emscripten_run_script("window.simulateAxisMotion(0, 0, 0)");
+ assertJoystickEvent(0, SDL_JOYAXISMOTION, 0, 0);
+ assert(SDL_JoystickGetAxis(pad1, 0) == 0);
+ emscripten_run_script("window.simulateAxisMotion(0, 1, -1)");
+ assertJoystickEvent(0, SDL_JOYAXISMOTION, 1, -32768);
+ assert(SDL_JoystickGetAxis(pad1, 1) == -32768);
+ emscripten_run_script("window.simulateAxisMotion(0, 1, -1)");
+ // No joystick change: Should not result in a new event.
+ assertNoJoystickEvent();
+ // Joystick 1 is not opened; should not result in a new event.
+ emscripten_run_script("window.simulateAxisMotion(1, 1, -1)");
+ assertNoJoystickEvent();
+
+ SDL_JoystickClose(pad1);
+ assert(!SDL_JoystickOpened(0));
+
+ // Joystick 0 is closed; we should not process any new gamepad events from it.
+ emscripten_run_script("window.simulateGamepadButtonDown(0, 1)");
+ assertNoJoystickEvent();
+
+ // End test.
+ result = 2;
+ printf("Test passed!\n");
+ REPORT_RESULT();
+}
+
diff --git a/tests/test_benchmark.py b/tests/test_benchmark.py
index e9cfee52..d19afb8d 100644
--- a/tests/test_benchmark.py
+++ b/tests/test_benchmark.py
@@ -119,9 +119,10 @@ process(sys.argv[1])
try_delete(final_filename)
output = Popen([PYTHON, EMCC, filename, #'-O3',
'-O2', '-s', 'DOUBLE_MODE=0', '-s', 'PRECISE_I64_MATH=0',
- '--llvm-lto', '3', '--memory-init-file', '0', '--js-transform', 'python hardcode.py',
+ '--memory-init-file', '0', '--js-transform', 'python hardcode.py',
'-s', 'TOTAL_MEMORY=128*1024*1024',
'--closure', '1',
+ #'-s', 'PRECISE_F32=1',
#'-g',
'-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]
@@ -428,10 +429,15 @@ process(sys.argv[1])
src = open(path_from_root('tests', 'life.c'), 'r').read()
self.do_benchmark('life', src, '''--------------------------------''', shared_args=['-std=c99'], force_c=True)
- def test_linpack(self):
+ def test_linpack_double(self):
def output_parser(output):
return 100.0/float(re.search('Unrolled Double Precision +([\d\.]+) Mflops', output).group(1))
- self.do_benchmark('linpack', open(path_from_root('tests', 'linpack.c')).read(), '''Unrolled Double Precision''', force_c=True, output_parser=output_parser)
+ self.do_benchmark('linpack_double', open(path_from_root('tests', 'linpack.c')).read(), '''Unrolled Double Precision''', force_c=True, output_parser=output_parser)
+
+ def test_linpack_float(self):
+ def output_parser(output):
+ return 100.0/float(re.search('Unrolled Single Precision +([\d\.]+) Mflops', output).group(1))
+ self.do_benchmark('linpack_float', open(path_from_root('tests', 'linpack.c')).read(), '''Unrolled Single Precision''', force_c=True, output_parser=output_parser, shared_args=['-DSP'])
def test_zzz_java_nbody(self): # tests xmlvm compiled java, including bitcasts of doubles, i64 math, etc.
args = [path_from_root('tests', 'nbody-java', x) for x in os.listdir(path_from_root('tests', 'nbody-java')) if x.endswith('.c')] + \
@@ -504,4 +510,4 @@ process(sys.argv[1])
native_args = native_lib + ['-I' + path_from_root('tests', 'bullet', 'src'),
'-I' + path_from_root('tests', 'bullet', 'Demos', 'Benchmarks')]
- self.do_benchmark('bullet', src, '\nok.\n', emcc_args=emcc_args, native_args=native_args) \ No newline at end of file
+ self.do_benchmark('bullet', src, '\nok.\n', emcc_args=emcc_args, native_args=native_args)
diff --git a/tests/test_browser.py b/tests/test_browser.py
index d52f109f..1900e2cf 100644
--- a/tests/test_browser.py
+++ b/tests/test_browser.py
@@ -874,6 +874,82 @@ keydown(100);keyup(100); // trigger the end
def test_glut_wheelevents(self):
self.btest('glut_wheelevents.c', '1')
+ def test_sdl_joystick_1(self):
+ # Generates events corresponding to the Working Draft of the HTML5 Gamepad API.
+ # http://www.w3.org/TR/2012/WD-gamepad-20120529/#gamepad-interface
+ open(os.path.join(self.get_dir(), 'pre.js'), 'w').write('''
+ var gamepads = [];
+ // Spoof this function.
+ navigator['getGamepads'] = function() {
+ return gamepads;
+ };
+ window['addNewGamepad'] = function(id, numAxes, numButtons) {
+ var index = gamepads.length;
+ gamepads.push({
+ axes: new Array(numAxes),
+ buttons: new Array(numButtons),
+ id: id,
+ index: index
+ });
+ var i;
+ for (i = 0; i < numAxes; i++) gamepads[index].axes[i] = 0;
+ for (i = 0; i < numButtons; i++) gamepads[index].buttons[i] = 0;
+ };
+ window['simulateGamepadButtonDown'] = function (index, button) {
+ gamepads[index].buttons[button] = 1;
+ };
+ window['simulateGamepadButtonUp'] = function (index, button) {
+ gamepads[index].buttons[button] = 0;
+ };
+ window['simulateAxisMotion'] = function (index, axis, value) {
+ gamepads[index].axes[axis] = value;
+ };
+ ''')
+ open(os.path.join(self.get_dir(), 'sdl_joystick.c'), 'w').write(self.with_report_result(open(path_from_root('tests', 'sdl_joystick.c')).read()))
+
+ Popen([PYTHON, EMCC, os.path.join(self.get_dir(), 'sdl_joystick.c'), '-O2', '--minify', '0', '-o', 'page.html', '--pre-js', 'pre.js']).communicate()
+ self.run_browser('page.html', '', '/report_result?2')
+
+ def test_sdl_joystick_2(self):
+ # Generates events corresponding to the Editor's Draft of the HTML5 Gamepad API.
+ # https://dvcs.w3.org/hg/gamepad/raw-file/default/gamepad.html#idl-def-Gamepad
+ open(os.path.join(self.get_dir(), 'pre.js'), 'w').write('''
+ var gamepads = [];
+ // Spoof this function.
+ navigator['getGamepads'] = function() {
+ return gamepads;
+ };
+ window['addNewGamepad'] = function(id, numAxes, numButtons) {
+ var index = gamepads.length;
+ gamepads.push({
+ axes: new Array(numAxes),
+ buttons: new Array(numButtons),
+ id: id,
+ index: index
+ });
+ var i;
+ for (i = 0; i < numAxes; i++) gamepads[index].axes[i] = 0;
+ // Buttons are objects
+ for (i = 0; i < numButtons; i++) gamepads[index].buttons[i] = { pressed: false, value: 0 };
+ };
+ // FF mutates the original objects.
+ window['simulateGamepadButtonDown'] = function (index, button) {
+ gamepads[index].buttons[button].pressed = true;
+ gamepads[index].buttons[button].value = 1;
+ };
+ window['simulateGamepadButtonUp'] = function (index, button) {
+ gamepads[index].buttons[button].pressed = false;
+ gamepads[index].buttons[button].value = 0;
+ };
+ window['simulateAxisMotion'] = function (index, axis, value) {
+ gamepads[index].axes[axis] = value;
+ };
+ ''')
+ open(os.path.join(self.get_dir(), 'sdl_joystick.c'), 'w').write(self.with_report_result(open(path_from_root('tests', 'sdl_joystick.c')).read()))
+
+ Popen([PYTHON, EMCC, os.path.join(self.get_dir(), 'sdl_joystick.c'), '-O2', '--minify', '0', '-o', 'page.html', '--pre-js', 'pre.js']).communicate()
+ self.run_browser('page.html', '', '/report_result?2')
+
def test_webgl_context_attributes(self):
# Javascript code to check the attributes support we want to test in the WebGL implementation
# (request the attribute, create a context and check its value afterwards in the context attributes).
diff --git a/tests/test_core.py b/tests/test_core.py
index b2147d49..37179ff1 100644
--- a/tests/test_core.py
+++ b/tests/test_core.py
@@ -882,6 +882,32 @@ nada
'''
self.do_run(src, 'OK!\n');
+ def test_float32_precise(self):
+ Settings.PRECISE_F32 = 1
+
+ src = r'''
+ #include <stdio.h>
+
+ int main(int argc, char **argv) {
+ float x = 1.23456789123456789;
+ float y = 5.20456089123406709;
+ while (argc > 10 || argc % 19 == 15) {
+ // confuse optimizer
+ x /= y;
+ y = 2*y - 1;
+ argc--;
+ }
+ x = x - y;
+ y = 3*y - x/2;
+ x = x*y;
+ y += 0.000000000123123123123;
+ x -= y/7.654;
+ printf("\n%.20f, %.20f\n", x, y);
+ return 0;
+ }
+ '''
+ self.do_run(src, '\n-72.16590881347656250000, 17.59867858886718750000\n')
+
def test_negative_zero(self):
src = r'''
#include <stdio.h>
@@ -1490,7 +1516,7 @@ f6: nan
#include <stdio.h>
#include <stdlib.h>
#include <cmath>
- int main()
+ int main(int argc, char **argv)
{
printf("*%.2f,%.2f,%d", M_PI, -M_PI, (1/0.0) > 1e300); // could end up as infinity, or just a very very big number
printf(",%d", isfinite(NAN) != 0);
@@ -1512,11 +1538,15 @@ f6: nan
sincosf(0.0, &fsine, &fcosine);
printf(",%1.1f", fsine);
printf(",%1.1f", fcosine);
+ fsine = sinf(1.1 + argc - 1);
+ fcosine = cosf(1.1 + argc - 1);
+ printf(",%1.1f", fsine);
+ printf(",%1.1f", fcosine);
printf("*\\n");
return 0;
}
'''
- self.do_run(src, '*3.14,-3.14,1,0,0,0,1,0,1,1,0,2,3,0.0,1.0,0.0,1.0*')
+ self.do_run(src, '*3.14,-3.14,1,0,0,0,1,0,1,1,0,2,3,0.0,1.0,0.0,1.0,0.9,0.5*')
def test_erf(self):
src = '''
@@ -3821,6 +3851,10 @@ def process(filename):
double get() {
double ret = 0;
__asm __volatile__("Math.abs(-12/3.3)":"=r"(ret)); // write to a variable
+ asm("#comment1");
+ asm volatile("#comment2");
+ asm volatile("#comment3\n"
+ "#comment4\n");
return ret;
}
@@ -3839,6 +3873,9 @@ def process(filename):
'''
self.do_run(src, 'Inline JS is very cool\n3.64\n') # TODO 1\n2\n3\n1\n2\n3\n')
+ if self.emcc_args == []: # opts will eliminate the comments
+ out = open('src.cpp.o.js').read()
+ for i in range(1, 5): assert ('comment%d' % i) in out
def test_inlinejs2(self):
if not self.is_le32(): return self.skip('le32 needed for inline js')
@@ -8328,9 +8365,14 @@ extern "C" {
if self.emcc_args is None: return self.skip('requires emcc')
results = [ (1,'''GG*ctt**tgagc*'''), (20,'''GGCCGGGCGCGGTGGCTCACGCCTGTAATCCCAGCACTTT*cttBtatcatatgctaKggNcataaaSatgtaaaDcDRtBggDtctttataattcBgtcg**tacgtgtagcctagtgtttgtgttgcgttatagtctatttgtggacacagtatggtcaaa**tgacgtcttttgatctgacggcgttaacaaagatactctg*'''),
(50,'''GGCCGGGCGCGGTGGCTCACGCCTGTAATCCCAGCACTTTGGGAGGCCGAGGCGGGCGGA*TCACCTGAGGTCAGGAGTTCGAGACCAGCCTGGCCAACAT*cttBtatcatatgctaKggNcataaaSatgtaaaDcDRtBggDtctttataattcBgtcg**tactDtDagcctatttSVHtHttKtgtHMaSattgWaHKHttttagacatWatgtRgaaa**NtactMcSMtYtcMgRtacttctWBacgaa**agatactctgggcaacacacatacttctctcatgttgtttcttcggacctttcataacct**ttcctggcacatggttagctgcacatcacaggattgtaagggtctagtggttcagtgagc**ggaatatcattcgtcggtggtgttaatctatctcggtgtagcttataaatgcatccgtaa**gaatattatgtttatttgtcggtacgttcatggtagtggtgtcgccgatttagacgtaaa**ggcatgtatg*''') ]
- for i, j in results:
- src = open(path_from_root('tests', 'fasta.cpp'), 'r').read()
- self.do_run(src, j, [str(i)], lambda x, err: x.replace('\n', '*'), no_build=i>1)
+ for precision in [0, 1, 2]:
+ Settings.PRECISE_F32 = precision
+ for t in ['float', 'double']:
+ print precision, t
+ src = open(path_from_root('tests', 'fasta.cpp'), 'r').read().replace('double', t)
+ for i, j in results:
+ self.do_run(src, j, [str(i)], lambda x, err: x.replace('\n', '*'), no_build=i>1)
+ shutil.copyfile('src.cpp.o.js', '%d_%s.js' % (precision, t))
def test_whets(self):
if not Settings.ASM_JS: return self.skip('mainly a test for asm validation here')
@@ -10705,6 +10747,7 @@ o2 = make_run("o2", compiler=CLANG, emcc_args=["-O2", "-s", "ASM_JS=0", "-s", "J
# asm.js
asm1 = make_run("asm1", compiler=CLANG, emcc_args=["-O1"])
asm2 = make_run("asm2", compiler=CLANG, emcc_args=["-O2"])
+asm2f = make_run("asm2f", compiler=CLANG, emcc_args=["-O2", "-s", "PRECISE_F32=1"])
asm2g = make_run("asm2g", compiler=CLANG, emcc_args=["-O2", "-g", "-s", "ASSERTIONS=1", "--memory-init-file", "1", "-s", "CHECK_HEAP_ALIGN=1"])
asm2x86 = make_run("asm2x86", compiler=CLANG, emcc_args=["-O2", "-g", "-s", "CHECK_HEAP_ALIGN=1"], env={"EMCC_LLVM_TARGET": "i386-pc-linux-gnu"})