diff options
-rw-r--r-- | AUTHORS | 2 | ||||
-rwxr-xr-x | emcc | 8 | ||||
-rw-r--r-- | src/jsifier.js | 2 | ||||
-rw-r--r-- | src/library.js | 8 | ||||
-rw-r--r-- | src/library_sdl.js | 11 | ||||
-rw-r--r-- | src/relooper/Relooper.cpp | 2 | ||||
-rw-r--r-- | system/include/bsd/float.h | 18 | ||||
-rw-r--r-- | system/include/libc/sys/dirent.h | 16 | ||||
-rw-r--r-- | system/lib/libc.symbols | 2 | ||||
-rw-r--r-- | system/lib/libc/gen/warn.c | 2 | ||||
-rw-r--r-- | tests/float+.c | 143 | ||||
-rwxr-xr-x | tests/runner.py | 61 | ||||
-rw-r--r-- | tests/sdl_audio_mix.c | 12 | ||||
-rw-r--r-- | tests/sounds/noise.ogg | bin | 0 -> 9205 bytes | |||
-rw-r--r-- | tools/file_packager.py | 40 | ||||
-rw-r--r-- | tools/shared.py | 13 |
16 files changed, 300 insertions, 40 deletions
@@ -83,6 +83,8 @@ 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> + @@ -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]) diff --git a/src/jsifier.js b/src/jsifier.js index 156fd65d..faef88d5 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_) { diff --git a/src/library.js b/src/library.js index f958a436..151cf3e5 100644 --- a/src/library.js +++ b/src/library.js @@ -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 { diff --git a/src/library_sdl.js b/src/library_sdl.js index a131f424..5aaddb3b 100644 --- a/src/library_sdl.js +++ b/src/library_sdl.js @@ -965,6 +965,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); @@ -1810,7 +1817,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 +1844,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/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/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/runner.py b/tests/runner.py index 2f755edd..f22fd86b 100755 --- a/tests/runner.py +++ b/tests/runner.py @@ -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') @@ -10496,6 +10501,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. @@ -11804,6 +11827,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 +11854,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 +11883,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 +11908,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 +12313,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): 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/sounds/noise.ogg b/tests/sounds/noise.ogg Binary files differnew file mode 100644 index 00000000..c53d49a7 --- /dev/null +++ b/tests/sounds/noise.ogg diff --git a/tools/file_packager.py b/tools/file_packager.py index 1443d165..99180b93 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('.'): + 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 = {} diff --git a/tools/shared.py b/tools/shared.py index 8a172d9c..b212a9cc 100644 --- a/tools/shared.py +++ b/tools/shared.py @@ -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(): |