import shutil, time, os, sys, json, tempfile, copy, shlex, atexit, subprocess
from subprocess import Popen, PIPE, STDOUT
from tempfile import mkstemp
__rootpath__ = os.path.abspath(os.path.dirname(os.path.dirname(__file__)))
def path_from_root(*pathelems):
return os.path.join(__rootpath__, *pathelems)
# Emscripten configuration is done through the EM_CONFIG environment variable.
# If the string value contained in this environment variable contains newline
# separated definitions, then these definitions will be used to configure
# Emscripten. Otherwise, the string is understood to be a path to a settings
# file that contains the required definitions.
EM_CONFIG = os.environ.get('EM_CONFIG')
if not EM_CONFIG:
EM_CONFIG = '~/.emscripten'
if '\n' in EM_CONFIG:
CONFIG_FILE = None
else:
CONFIG_FILE = os.path.expanduser(EM_CONFIG)
if not os.path.exists(CONFIG_FILE):
config_file = open(path_from_root('tools', 'settings_template_readonly.py')).read().split('\n')
config_file = config_file[1:] # remove "this file will be copied..."
config_file = '\n'.join(config_file)
# autodetect some default paths
config_file = config_file.replace('{{{ EMSCRIPTEN_ROOT }}}', __rootpath__)
llvm_root = '/usr/bin'
try:
llvm_root = os.path.dirname(Popen(['which', 'clang'], stdout=PIPE).communicate()[0].replace('\n', ''))
except:
pass
config_file = config_file.replace('{{{ LLVM_ROOT }}}', llvm_root)
node = 'node'
try:
node = Popen(['which', 'node'], stdout=PIPE).communicate()[0].replace('\n', '')
except:
pass
config_file = config_file.replace('{{{ NODE }}}', node)
# write
open(CONFIG_FILE, 'w').write(config_file)
print >> sys.stderr, '''
==============================================================================
Welcome to Emscripten!
This is the first time any of the Emscripten tools has been run.
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
NODE_JS = %s
EMSCRIPTEN_ROOT = %s
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__)
sys.exit(0)
try:
config_text = open(CONFIG_FILE, 'r').read() if CONFIG_FILE else EM_CONFIG
exec(config_text)
except Exception, e:
print >> sys.stderr, 'Error in evaluating %s (at %s): %s, text: %s' % (EM_CONFIG, CONFIG_FILE, str(e), config_text)
sys.exit(1)
# Expectations
EXPECTED_LLVM_VERSION = (3,1)
def check_clang_version():
expected = 'clang version ' + '.'.join(map(str, EXPECTED_LLVM_VERSION))
actual = Popen([CLANG, '-v'], stderr=PIPE).communicate()[1].split('\n')[0]
if expected in actual:
return True
print >> sys.stderr, 'warning: LLVM version appears incorrect (seeing "%s", expected "%s")' % (actual, expected)
return False
def check_llvm_version():
try:
check_clang_version();
except Exception, e:
print >> sys.stderr, 'warning: Could not verify LLVM version: %s' % str(e)
# Check that basic stuff we need (a JS engine to compile, Node.js, and Clang and LLVM)
# exists.
# The test runner always does this check (through |force|). emcc does this less frequently,
# only when ${EM_CONFIG}_sanity does not exist or is older than EM_CONFIG (so,
# we re-check sanity when the settings are changed)
def check_sanity(force=False):
try:
if not force:
if not CONFIG_FILE:
return # config stored directly in EM_CONFIG => skip sanity checks
settings_mtime = os.stat(CONFIG_FILE).st_mtime
sanity_file = CONFIG_FILE + '_sanity'
try:
sanity_mtime = os.stat(sanity_file).st_mtime
if sanity_mtime > settings_mtime:
return # sanity has been checked
except:
pass
print >> sys.stderr, '(Emscripten: Config file changed, clearing cache)' # LLVM may have changed, etc.
Cache.erase()
check_llvm_version() # just a warning, not a fatal check - do it even if EM_IGNORE_SANITY is on
if os.environ.get('EM_IGNORE_SANITY'):
print >> sys.stderr, 'EM_IGNORE_SANITY set, ignoring sanity checks'
return
print >> sys.stderr, '(Emscripten: Running sanity checks)'
if not check_engine(COMPILER_ENGINE):
print >> sys.stderr, 'FATAL: The JavaScript shell used for compiling (%s) does not seem to work, check the paths in %s' % (COMPILER_ENGINE, EM_CONFIG)
sys.exit(0)
if NODE_JS != COMPILER_ENGINE:
if not check_engine(NODE_JS):
print >> sys.stderr, 'FATAL: Node.js (%s) does not seem to work, check the paths in %s' % (NODE_JS, EM_CONFIG)
sys.exit(0)
for cmd in [CLA