diff options
Diffstat (limited to 'tools')
-rwxr-xr-x | tools/bindings_generator.py | 2 | ||||
-rw-r--r-- | tools/eliminator/eliminator-test-output.js | 8 | ||||
-rw-r--r-- | tools/eliminator/eliminator-test.js | 12 | ||||
-rwxr-xr-x | tools/emconfiguren.py | 2 | ||||
-rwxr-xr-x | tools/emmaken.py | 2 | ||||
-rwxr-xr-x | tools/emmakenxx.py | 4 | ||||
-rwxr-xr-x | tools/exec_llvm.py | 2 | ||||
-rwxr-xr-x | tools/fix_closure.py | 2 | ||||
-rw-r--r-- | tools/js-optimizer.js | 2 | ||||
-rwxr-xr-x | tools/ll-strip.py | 2 | ||||
-rw-r--r-- | tools/make_minigzip.py | 2 | ||||
-rw-r--r-- | tools/namespacer.py | 2 | ||||
-rwxr-xr-x | tools/nativize_llvm.py | 2 | ||||
-rwxr-xr-x | tools/reproduceriter.py | 2 | ||||
-rw-r--r-- | tools/scons/site_scons/site_tools/emscripten/__init__.py | 2 | ||||
-rw-r--r-- | tools/scons/site_scons/site_tools/emscripten/emscripten.py | 2 | ||||
-rw-r--r-- | tools/settings_template_readonly.py | 1 | ||||
-rw-r--r-- | tools/shared.py | 77 |
18 files changed, 82 insertions, 46 deletions
diff --git a/tools/bindings_generator.py b/tools/bindings_generator.py index 0c7c814f..d2c165a2 100755 --- a/tools/bindings_generator.py +++ b/tools/bindings_generator.py @@ -1,4 +1,4 @@ -#!/usr/bin/env python +#!/usr/bin/env python2 ''' Use CppHeaderParser to parse some C++ headers, and generate binding code for them. diff --git a/tools/eliminator/eliminator-test-output.js b/tools/eliminator/eliminator-test-output.js index ede34103..01f092d5 100644 --- a/tools/eliminator/eliminator-test-output.js +++ b/tools/eliminator/eliminator-test-output.js @@ -6132,4 +6132,12 @@ function _mallocNoU($bytes) { return $mem_0; return null; } +function phi() { + if (wat()) { + var $10 = 1; + } else { + var $10 = (_init_mparams() | 0) != 0; + } + var $10; +} diff --git a/tools/eliminator/eliminator-test.js b/tools/eliminator/eliminator-test.js index e44f28ad..8b376305 100644 --- a/tools/eliminator/eliminator-test.js +++ b/tools/eliminator/eliminator-test.js @@ -8828,5 +8828,15 @@ function _mallocNoU($bytes) { return $mem_0; return null; } -// EMSCRIPTEN_GENERATED_FUNCTIONS: ["a", "b", "c", "f", "g", "h", "py", "r", "t", "f2", "f3", "llvm3_1", "_inflate", "_malloc", "_mallocNoU"] +function phi() { + if (wat()) { + var $10 = 1; + } else { + var $7=_init_mparams(); + var $8=(($7)|0)!=0; + var $10 = $8; + } + var $10; +} +// EMSCRIPTEN_GENERATED_FUNCTIONS: ["a", "b", "c", "f", "g", "h", "py", "r", "t", "f2", "f3", "llvm3_1", "_inflate", "_malloc", "_mallocNoU", "asm", "phi"] diff --git a/tools/emconfiguren.py b/tools/emconfiguren.py index fd7b7549..35d83b87 100755 --- a/tools/emconfiguren.py +++ b/tools/emconfiguren.py @@ -1,4 +1,4 @@ -#!/usr/bin/env python +#!/usr/bin/env python2 import sys print >> sys.stderr, '\n\nemconfiguren.py is deprecated! use "emconfigure"\n\n' diff --git a/tools/emmaken.py b/tools/emmaken.py index ae4794f0..77405761 100755 --- a/tools/emmaken.py +++ b/tools/emmaken.py @@ -1,4 +1,4 @@ -#!/usr/bin/env python +#!/usr/bin/env python2 import sys print >> sys.stderr, '\n\nemmaken.py is deprecated! use "emcc"\n\n' diff --git a/tools/emmakenxx.py b/tools/emmakenxx.py index 1c31f3c2..0af3f99e 100755 --- a/tools/emmakenxx.py +++ b/tools/emmakenxx.py @@ -1,4 +1,4 @@ -#!/usr/bin/env python +#!/usr/bin/env python2 ''' see emmaken.py @@ -14,5 +14,5 @@ from tools.shared import * emmaken = path_from_root('tools', 'emmaken.py') os.environ['EMMAKEN_CXX'] = '1' -exit(subprocess.call(['python', emmaken] + sys.argv[1:])) +exit(subprocess.call([PYTHON, emmaken] + sys.argv[1:])) diff --git a/tools/exec_llvm.py b/tools/exec_llvm.py index 71c0f18d..2685f9e4 100755 --- a/tools/exec_llvm.py +++ b/tools/exec_llvm.py @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/python2 ''' Small utility to execute some llvm bitcode. diff --git a/tools/fix_closure.py b/tools/fix_closure.py index ab2dacbc..91d2a866 100755 --- a/tools/fix_closure.py +++ b/tools/fix_closure.py @@ -1,4 +1,4 @@ -#!/usr/bin/env python +#!/usr/bin/env python2 ''' With very very large projects, closure compiler can translate FUNCTION_TABLE into something like diff --git a/tools/js-optimizer.js b/tools/js-optimizer.js index 29aecdcf..62161738 100644 --- a/tools/js-optimizer.js +++ b/tools/js-optimizer.js @@ -1464,7 +1464,7 @@ function eliminate(ast, memSafe) { for (var name in locals) { if (definitions[name] == 1 && uses[name] == 1) { potentials[name] = 1; - } else if (uses[name] == 0) { + } else if (uses[name] == 0 && (!definitions[name] || definitions[name] <= 1)) { // no uses, no def or 1 def (cannot operate on phis, and the llvm optimizer will remove unneeded phis anyhow) var hasSideEffects = false; if (values[name]) { traverse(values[name], function(node, type) { diff --git a/tools/ll-strip.py b/tools/ll-strip.py index b03e4f3a..a08da478 100755 --- a/tools/ll-strip.py +++ b/tools/ll-strip.py @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/python2 import sys, re diff --git a/tools/make_minigzip.py b/tools/make_minigzip.py index 60177318..0c96457b 100644 --- a/tools/make_minigzip.py +++ b/tools/make_minigzip.py @@ -9,5 +9,5 @@ zlib = shared.Building.build_library('zlib', shared.EMSCRIPTEN_TEMP_DIR, shared. print 'Building minigzip' -Popen(['python', shared.EMCC, '-O2', shared.path_from_root('tests', 'zlib', 'minigzip.c'), zlib, '-o', shared.path_from_root('tools', 'minigzip.js')]).communicate() +Popen(['python2', shared.EMCC, '-O2', shared.path_from_root('tests', 'zlib', 'minigzip.c'), zlib, '-o', shared.path_from_root('tools', 'minigzip.js')]).communicate() diff --git a/tools/namespacer.py b/tools/namespacer.py index 810689eb..81b8d2d1 100644 --- a/tools/namespacer.py +++ b/tools/namespacer.py @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/python2 ''' Tool that generates namespace boilerplate. Given diff --git a/tools/nativize_llvm.py b/tools/nativize_llvm.py index de78dce2..e76b9a4e 100755 --- a/tools/nativize_llvm.py +++ b/tools/nativize_llvm.py @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/env python2 ''' Small utility to build some llvm bitcode into native code. Useful when lli (called diff --git a/tools/reproduceriter.py b/tools/reproduceriter.py index 058eeecf..c820978b 100755 --- a/tools/reproduceriter.py +++ b/tools/reproduceriter.py @@ -1,4 +1,4 @@ -#!/usr/bin/env python +#!/usr/bin/env python2 ''' Reproducer Rewriter diff --git a/tools/scons/site_scons/site_tools/emscripten/__init__.py b/tools/scons/site_scons/site_tools/emscripten/__init__.py index 8ae2288e..ebd2c21b 100644 --- a/tools/scons/site_scons/site_tools/emscripten/__init__.py +++ b/tools/scons/site_scons/site_tools/emscripten/__init__.py @@ -1,3 +1,3 @@ -#!/usr/bin/env python +#!/usr/bin/env python2 from emscripten import exists, generate diff --git a/tools/scons/site_scons/site_tools/emscripten/emscripten.py b/tools/scons/site_scons/site_tools/emscripten/emscripten.py index ce704bf8..5abd4fee 100644 --- a/tools/scons/site_scons/site_tools/emscripten/emscripten.py +++ b/tools/scons/site_scons/site_tools/emscripten/emscripten.py @@ -1,4 +1,4 @@ -#!/usr/bin/env python +#!/usr/bin/env python2 import os diff --git a/tools/settings_template_readonly.py b/tools/settings_template_readonly.py index 93ea2036..970a8f8c 100644 --- a/tools/settings_template_readonly.py +++ b/tools/settings_template_readonly.py @@ -7,6 +7,7 @@ import os # this helps projects using emscripten find it EMSCRIPTEN_ROOT = os.path.expanduser(os.getenv('EMSCRIPTEN') or '{{{ EMSCRIPTEN_ROOT }}}') LLVM_ROOT = os.path.expanduser(os.getenv('LLVM') or '{{{ LLVM_ROOT }}}') +PYTHON = os.path.expanduser(os.getenv('PYTHON') or '{{{ PYTHON }}}') # See below for notes on which JS engine(s) you need NODE_JS = os.path.expanduser(os.getenv('NODE') or '{{{ NODE }}}') diff --git a/tools/shared.py b/tools/shared.py index 1dec21cd..72629131 100644 --- a/tools/shared.py +++ b/tools/shared.py @@ -92,10 +92,16 @@ else: node = 'node' try: node = Popen(['which', 'node'], stdout=PIPE).communicate()[0].replace('\n', '') or \ - Popen(['which', 'nodejs'], stdout=PIPE).communicate()[0].replace('\n', '') + Popen(['which', 'nodejs'], stdout=PIPE).communicate()[0].replace('\n', '') or node except: pass config_file = config_file.replace('{{{ NODE }}}', node) + python = 'python' + try: + python = Popen(['which', 'python'], stdout=PIPE).communicate()[0].replace('\n', '') + except: + pass + config_file = config_file.replace('{{{ PYTHON }}}', python) # write open(CONFIG_FILE, 'w').write(config_file) @@ -110,6 +116,7 @@ A settings file has been copied to %s, at absolute path: %s It contains our best guesses for the important paths, which are: LLVM_ROOT = %s + PYTHON = %s NODE_JS = %s EMSCRIPTEN_ROOT = %s @@ -117,7 +124,7 @@ Please edit the file if any of those are incorrect. This command will now exit. When you are done editing those paths, re-run it. ============================================================================== -''' % (EM_CONFIG, CONFIG_FILE, llvm_root, node, __rootpath__) +''' % (EM_CONFIG, CONFIG_FILE, llvm_root, python, node, __rootpath__) sys.exit(0) try: config_text = open(CONFIG_FILE, 'r').read() if CONFIG_FILE else EM_CONFIG @@ -128,7 +135,7 @@ except Exception, e: # Expectations -EXPECTED_LLVM_VERSION = (3,1) +EXPECTED_LLVM_VERSION = (3,2) def check_clang_version(): expected = 'clang version ' + '.'.join(map(str, EXPECTED_LLVM_VERSION)) @@ -165,7 +172,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.0.1a' +EMSCRIPTEN_VERSION = '1.1.0' def check_sanity(force=False): try: @@ -319,6 +326,12 @@ except: CLOSURE_COMPILER = path_from_root('third_party', 'closure-compiler', 'compiler.jar') try: + PYTHON +except: + print >> sys.stderr, 'PYTHON not defined in ~/.emscripten, using "python"' + PYTHON = 'python' + +try: JAVA except: print >> sys.stderr, 'JAVA not defined in ~/.emscripten, using "java"' @@ -333,7 +346,7 @@ except: # Force a simple, standard target as much as possible: target 32-bit linux, and disable various flags that hint at other platforms COMPILER_OPTS = COMPILER_OPTS + ['-m32', '-U__i386__', '-U__x86_64__', '-U__i386', '-U__x86_64', '-U__SSE__', '-U__SSE2__', '-U__MMX__', '-UX87_DOUBLE_ROUNDING', '-UHAVE_GCC_ASM_FOR_X87', '-DEMSCRIPTEN', '-U__STRICT_ANSI__', '-U__CYGWIN__', - '-D__STDC__', '-Xclang', '-triple=i386-pc-linux-gnu', '-D__IEEE_LITTLE_ENDIAN'] + '-D__STDC__', '-Xclang', '-triple=i386-pc-linux-gnu', '-D__IEEE_LITTLE_ENDIAN', '-fno-math-errno'] USE_EMSDK = not os.environ.get('EMMAKEN_NO_SDK') @@ -498,6 +511,14 @@ def read_pgo_data(filename): 'overflows_lines': overflows_lines } +def unique_ordered(values): # return a list of unique values in an input list, without changing order (list(set(.)) would change order randomly) + seen = set() + def check(value): + if value in seen: return False + seen.add(value) + return True + return filter(check, values) + # Settings. A global singleton. Not pretty, but nicer than passing |, settings| everywhere class Settings: @@ -712,7 +733,7 @@ set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE ONLY)''' % { 'winfix': '' if not WINDOWS e Popen([LLVM_EXTRACT, filename, '-delete', '-func=' + symbol, '-o', filename], stderr=PIPE).communicate() @staticmethod - def link(files, target, remove_duplicates=False): + def link(files, target): actual_files = [] unresolved_symbols = set(['main']) # tracking unresolveds is necessary for .a linking, see below. (and main is always a necessary symbol) resolved_symbols = set() @@ -773,26 +794,11 @@ set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE ONLY)''' % { 'winfix': '' if not WINDOWS e os.chdir(cwd) try_delete(target) - if remove_duplicates: - # Remove duplicate symbols. This is a workaround for how we compile .a files, we try to - # emulate ld behavior which is permissive TODO: cache llvm-nm results - seen_symbols = set() - print >> sys.stderr, actual_files - for actual in actual_files: - symbols = Building.llvm_nm(actual) - dupes = seen_symbols.intersection(symbols.defs) - if len(dupes) > 0: - print >> sys.stderr, 'emcc: warning: removing duplicates in', actual - for dupe in dupes: - print >> sys.stderr, 'emcc: warning: removing duplicate', dupe - Building.remove_symbol(actual, dupe) - Popen([LLVM_EXTRACT, actual, '-delete', '-glob=.str', '-o', actual], stderr=PIPE).communicate() # garbage that appears here - seen_symbols = seen_symbols.union(symbols.defs) - # Finish link + actual_files = unique_ordered(actual_files) # tolerate people trying to link a.so a.so etc. if DEBUG: print >>sys.stderr, 'emcc: llvm-linking:', actual_files output = Popen([LLVM_LINK] + actual_files + ['-o', target], stdout=PIPE).communicate()[0] - assert os.path.exists(target) and (output is None or 'Could not open input file' not in output), 'Linking error: ' + output + '\nemcc: If you get duplicate symbol errors, try --remove-duplicates' + assert os.path.exists(target) and (output is None or 'Could not open input file' not in output), 'Linking error: ' + output for temp_dir in temp_dirs: try_delete(temp_dir) @@ -877,13 +883,13 @@ set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE ONLY)''' % { 'winfix': '' if not WINDOWS e if output_filename is None: output_filename = filename + '.o' try_delete(output_filename) - Popen(ENV_PREFIX + ['python', EMCC, filename] + args + ['-o', output_filename], stdout=stdout, stderr=stderr, env=env).communicate() + Popen([PYTHON, EMCC, filename] + args + ['-o', output_filename], stdout=stdout, stderr=stderr, env=env).communicate() assert os.path.exists(output_filename), 'emcc could not create output file' @staticmethod def emar(action, output_filename, filenames, stdout=None, stderr=None, env=None): try_delete(output_filename) - Popen(ENV_PREFIX + ['python', EMAR, action, output_filename] + filenames, stdout=stdout, stderr=stderr, env=env).communicate() + Popen([PYTHON, EMAR, action, output_filename] + filenames, stdout=stdout, stderr=stderr, env=env).communicate() if 'c' in action: assert os.path.exists(output_filename), 'emar could not create output file' @@ -894,7 +900,7 @@ set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE ONLY)''' % { 'winfix': '' if not WINDOWS e # Run Emscripten settings = Settings.serialize() - compiler_output = timeout_run(Popen(ENV_PREFIX + ['python', EMSCRIPTEN, filename + ('.o.ll' if append_ext else ''), '-o', filename + '.o.js'] + settings + extra_args, stdout=PIPE), None, 'Compiling') + compiler_output = timeout_run(Popen([PYTHON, EMSCRIPTEN, filename + ('.o.ll' if append_ext else ''), '-o', filename + '.o.js'] + settings + extra_args, stdout=PIPE), None, 'Compiling') #print compiler_output # Detect compilation crashes and errors @@ -916,6 +922,12 @@ set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE ONLY)''' % { 'winfix': '' if not WINDOWS e return Settings.INLINING_LIMIT == 0 @staticmethod + def get_safe_internalize(): + exports = ','.join(map(lambda exp: exp[1:], Settings.EXPORTED_FUNCTIONS)) + # internalize carefully, llvm 3.2 will remove even main if not told not to + return ['-internalize', '-internalize-public-api-list=' + exports] + + @staticmethod def pick_llvm_opts(optimization_level): ''' It may be safe to use nonportable optimizations (like -OX) if we remove the platform info from the .ll @@ -950,7 +962,7 @@ set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE ONLY)''' % { 'winfix': '' if not WINDOWS e opts.append('-basicaa') # makes fannkuch slow but primes fast if Building.can_build_standalone(): - opts.append('-internalize') + opts += Building.get_safe_internalize() opts.append('-globalopt') opts.append('-ipsccp') @@ -1059,7 +1071,7 @@ set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE ONLY)''' % { 'winfix': '' if not WINDOWS e Building._is_ar_cache[filename] = sigcheck return sigcheck except Exception, e: - print 'shared.Building.is_ar failed to test whether file \'%s\' is a llvm archive file! Failed on exception: %s' % (filename, e) + print >> sys.stderr, 'shared.Building.is_ar failed to test whether file \'%s\' is a llvm archive file! Failed on exception: %s' % (filename, e) return False @staticmethod @@ -1079,7 +1091,7 @@ set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE ONLY)''' % { 'winfix': '' if not WINDOWS e assert os.path.exists(test_ll) try_delete(test_ll) except Exception, e: - print 'shared.Building.is_bitcode failed to test whether file \'%s\' is a llvm bitcode file! Failed on exception: %s' % (filename, e) + print >> sys.stderr, 'shared.Building.is_bitcode failed to test whether file \'%s\' is a llvm bitcode file! Failed on exception: %s' % (filename, e) return False # look for magic signature @@ -1110,7 +1122,12 @@ set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE ONLY)''' % { 'winfix': '' if not WINDOWS e def make(opt_level): raw = RELOOPER + '.raw.js' - Building.emcc(os.path.join('relooper', 'Relooper.cpp'), ['-I' + os.path.join('relooper'), '--post-js', os.path.join('relooper', 'emscripten', 'glue.js'), '-s', 'TOTAL_MEMORY=52428800', '-s', 'DEFAULT_LIBRARY_FUNCS_TO_INCLUDE=["memcpy", "memset", "malloc", "free", "puts"]', '-O' + str(opt_level), '--closure', '0'], raw) + Building.emcc(os.path.join('relooper', 'Relooper.cpp'), ['-I' + os.path.join('relooper'), '--post-js', + os.path.join('relooper', 'emscripten', 'glue.js'), + '-s', 'TOTAL_MEMORY=52428800', + '-s', 'EXPORTED_FUNCTIONS=["_rl_set_output_buffer","_rl_make_output_buffer","_rl_new_block","_rl_delete_block","_rl_block_add_branch_to","_rl_new_relooper","_rl_delete_relooper","_rl_relooper_add_block","_rl_relooper_calculate","_rl_relooper_render"]', + '-s', 'DEFAULT_LIBRARY_FUNCS_TO_INCLUDE=["memcpy", "memset", "malloc", "free", "puts"]', + '-O' + str(opt_level), '--closure', '0'], raw) f = open(RELOOPER, 'w') f.write("// Relooper, (C) 2012 Alon Zakai, MIT license, https://github.com/kripken/Relooper\n") f.write("var Relooper = (function() {\n"); |