aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rwxr-xr-xemcc16
-rwxr-xr-xemscripten.py59
-rw-r--r--src/analyzer.js9
-rw-r--r--src/compiler.js11
-rw-r--r--src/headless.js5
-rw-r--r--src/jsifier.js56
-rw-r--r--src/library.js683
-rw-r--r--src/library_gl.js109
-rw-r--r--src/library_openal.js541
-rw-r--r--src/library_sdl.js29
-rw-r--r--src/long.js7
-rw-r--r--src/modules.js2
-rw-r--r--src/parseTools.js59
-rw-r--r--src/preamble.js49
-rw-r--r--src/runtime.js51
-rw-r--r--src/settings.js29
-rw-r--r--src/utility.js9
-rw-r--r--system/include/AL/al.h172
-rw-r--r--system/include/AL/alc.h84
-rw-r--r--system/include/libc/ctype.h23
-rw-r--r--system/include/libc/math.h27
-rw-r--r--tests/cases/alignedunaligned.ll6
-rw-r--r--tests/cases/breakinthemiddle3.ll26
-rw-r--r--tests/cases/callundef.ll18
-rw-r--r--tests/cases/phicubed.ll29
-rw-r--r--tests/cases/storestruct.ll5
-rw-r--r--tests/cases/unannotated__noasm.ll (renamed from tests/cases/unannotated.ll)0
-rw-r--r--tests/cases/unannotated__noasm.txt (renamed from tests/cases/unannotated.txt)0
-rw-r--r--tests/gl_ps_strides.c241
-rw-r--r--tests/gl_ps_strides.pngbin0 -> 98713 bytes
-rw-r--r--tests/openal_playback.cpp115
-rwxr-xr-xtests/runner.py239
-rw-r--r--tests/sdl_audio_mix.c2
-rw-r--r--tests/sounds/audio.wavbin0 -> 190764 bytes
-rwxr-xr-xtools/bindings_generator.py5
-rw-r--r--tools/js_optimizer.py2
-rw-r--r--tools/settings_template_readonly.py3
-rw-r--r--tools/shared.py6
38 files changed, 2154 insertions, 573 deletions
diff --git a/emcc b/emcc
index d06bb21c..488f0788 100755
--- a/emcc
+++ b/emcc
@@ -215,6 +215,20 @@ Options that are modified or new in %s include:
(without the external "s in either of those,
you would get an error)
+ You can also specify a file from which the
+ value would be read, for example,
+
+ -s DEAD_FUNCTIONS=@/path/to/file
+
+ The contents of /path/to/file will be read,
+ JSON.parsed and set into DEAD_FUNCTIONS (so
+ the file could contain
+
+ ["_func1", "func2"]
+
+ ). Note that the path must be absolute, not
+ relative.
+
-g Use debug info. Note that you need this during
the last compilation phase from bitcode to
JavaScript, or else we will remove it by
@@ -973,6 +987,8 @@ try:
# Apply -s settings in newargs here (after optimization levels, so they can override them)
for change in settings_changes:
key, value = change.split('=')
+ if value[0] == '@':
+ value = '"' + value + '"'
exec('shared.Settings.' + key + ' = ' + value)
# Apply effects from settings
diff --git a/emscripten.py b/emscripten.py
index bbc4f76d..c9d8505d 100755
--- a/emscripten.py
+++ b/emscripten.py
@@ -34,9 +34,13 @@ MIN_CHUNK_SIZE = 1024*1024
MAX_CHUNK_SIZE = float(os.environ.get('EMSCRIPT_MAX_CHUNK_SIZE') or 'inf') # configuring this is just for debugging purposes
def process_funcs((i, funcs, meta, settings_file, compiler, forwarded_file, libraries, compiler_engine, temp_files, DEBUG)):
- ll = ''.join(funcs) + '\n' + meta
funcs_file = temp_files.get('.func_%d.ll' % i).name
- open(funcs_file, 'w').write(ll)
+ f = open(funcs_file, 'w')
+ f.write(funcs)
+ funcs = None
+ f.write('\n')
+ f.write(meta)
+ f.close()
out = jsrun.run_js(
compiler,
engine=compiler_engine,
@@ -188,6 +192,8 @@ def emscript(infile, settings, outfile, libraries=[], compiler_engine=None,
funcs, chunk_size,
jcache.get_cachename('emscript_files') if jcache else None)
+ funcs = None
+
if jcache:
# load chunks from cache where we can # TODO: ignore small chunks
cached_outputs = []
@@ -223,6 +229,9 @@ def emscript(infile, settings, outfile, libraries=[], compiler_engine=None,
outputs = pool.map(process_funcs, commands, chunksize=1)
elif len(chunks) == 1:
outputs = [process_funcs(commands[0])]
+
+ commands = None
+
else:
outputs = []
@@ -235,6 +244,8 @@ def emscript(infile, settings, outfile, libraries=[], compiler_engine=None,
jcache.set(shortkey, keys, outputs[i])
if out and DEBUG and len(chunks) > 0: print >> sys.stderr, ' saving %d funcchunks to jcache' % len(chunks)
+ chunks = None
+
if jcache: outputs += cached_outputs # TODO: preserve order
outputs = [output.split('//FORWARDED_DATA:') for output in outputs]
@@ -258,8 +269,10 @@ def emscript(infile, settings, outfile, libraries=[], compiler_engine=None,
for key in curr_forwarded_json['Functions']['indexedFunctions'].iterkeys():
indexed_functions.add(key)
if settings.get('ASM_JS'):
+ export_bindings = settings['EXPORT_BINDINGS']
for key in curr_forwarded_json['Functions']['implementedFunctions'].iterkeys():
- if key in all_exported_functions: exported_implemented_functions.add(key)
+ if key in all_exported_functions or (export_bindings and key.startswith('_emscripten_bind')):
+ exported_implemented_functions.add(key)
for key, value in curr_forwarded_json['Functions']['unimplementedFunctions'].iteritems():
forwarded_json['Functions']['unimplementedFunctions'][key] = value
@@ -268,7 +281,7 @@ def emscript(infile, settings, outfile, libraries=[], compiler_engine=None,
if len(parts) > 1:
pre = parts[0]
outputs.append([parts[1]])
- funcs_js = ''.join([output[0] for output in outputs])
+ funcs_js = [''.join([output[0] for output in outputs])] # this will be a list of things, so we do not do string appending as we add more
outputs = None
if DEBUG: print >> sys.stderr, ' emscript: phase 2b took %s seconds' % (time.time() - t)
@@ -313,6 +326,10 @@ def emscript(infile, settings, outfile, libraries=[], compiler_engine=None,
last_forwarded_json = json.loads(last_forwarded_data)
if settings.get('ASM_JS'):
+ post_funcs, post_rest = post.split('// EMSCRIPTEN_END_FUNCS\n')
+ post = post_rest
+ funcs_js += ['\n' + post_funcs + '// EMSCRIPTEN_END_FUNCS\n']
+
simple = os.environ.get('EMCC_SIMPLE_ASM')
class Counter:
i = 0
@@ -320,11 +337,12 @@ def emscript(infile, settings, outfile, libraries=[], compiler_engine=None,
del last_forwarded_json['Functions']['tables']['pre']
# Find function table calls without function tables generated for them
- for use in set(re.findall(r'{{{ FTM_[\w\d_$]+ }}}', funcs_js)):
- sig = use[8:len(use)-4]
- if sig not in last_forwarded_json['Functions']['tables']:
- if DEBUG: print >> sys.stderr, 'add empty function table', sig
- last_forwarded_json['Functions']['tables'][sig] = 'var FUNCTION_TABLE_' + sig + ' = [0,0];\n'
+ for funcs_js_item in funcs_js:
+ for use in set(re.findall(r'{{{ FTM_[\w\d_$]+ }}}', funcs_js_item)):
+ sig = use[8:len(use)-4]
+ if sig not in last_forwarded_json['Functions']['tables']:
+ if DEBUG: print >> sys.stderr, 'add empty function table', sig
+ last_forwarded_json['Functions']['tables'][sig] = 'var FUNCTION_TABLE_' + sig + ' = [0,0];\n'
def make_table(sig, raw):
i = Counter.i
@@ -340,7 +358,7 @@ def emscript(infile, settings, outfile, libraries=[], compiler_engine=None,
asm_setup = ''
maths = ['Math.' + func for func in ['floor', 'abs', 'sqrt', 'pow', 'cos', 'sin', 'tan', 'acos', 'asin', 'atan', 'atan2', 'exp', 'log', 'ceil', 'imul']]
fundamentals = ['Math', 'Int8Array', 'Int16Array', 'Int32Array', 'Uint8Array', 'Uint16Array', 'Uint32Array', 'Float32Array', 'Float64Array']
- math_envs = ['Runtime.bitshift64', 'Math.min'] # TODO: move min to maths
+ 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]
if settings['SAFE_HEAP']: basic_funcs += ['SAFE_HEAP_LOAD', 'SAFE_HEAP_STORE', 'SAFE_HEAP_CLEAR']
@@ -411,9 +429,9 @@ var i64Math_modulo = function(a, b, c, d, e) { i64Math.modulo(a, b, c, d, e) };
# finalize
- if DEBUG: print >> sys.stderr, 'asm text sizes', len(funcs_js), len(asm_setup), len(asm_global_vars), len(asm_global_funcs), len(pre_tables), len('\n'.join(function_tables_impls)), len(function_tables_defs.replace('\n', '\n ')), len(exports), len(the_global), len(sending), len(receiving)
+ if DEBUG: print >> sys.stderr, 'asm text sizes', map(len, funcs_js), len(asm_setup), len(asm_global_vars), len(asm_global_funcs), len(pre_tables), len('\n'.join(function_tables_impls)), len(function_tables_defs.replace('\n', '\n ')), len(exports), len(the_global), len(sending), len(receiving)
- funcs_js = '''
+ funcs_js = ['''
%s
function asmPrintInt(x, y) {
Module.print('int ' + x + ',' + y);// + ' ' + new Error().stack);
@@ -463,7 +481,7 @@ var asm = (function(global, env, buffer) {
value = value|0;
tempRet%d = value;
}
-''' % (i, i) for i in range(10)]) + funcs_js + '''
+''' % (i, i) for i in range(10)])] + funcs_js + ['''
%s
return %s;
@@ -474,7 +492,7 @@ var asm = (function(global, env, buffer) {
Runtime.stackAlloc = function(size) { return asm.stackAlloc(size) };
Runtime.stackSave = function() { return asm.stackSave() };
Runtime.stackRestore = function(top) { asm.stackRestore(top) };
-''' % (pre_tables + '\n'.join(function_tables_impls) + '\n' + function_tables_defs.replace('\n', '\n '), exports, the_global, sending, receiving)
+''' % (pre_tables + '\n'.join(function_tables_impls) + '\n' + function_tables_defs.replace('\n', '\n '), exports, the_global, sending, receiving)]
# Set function table masks
def function_table_maskize(js):
@@ -487,17 +505,20 @@ Runtime.stackRestore = function(top) { asm.stackRestore(top) };
sig = m.groups(0)[0]
return masks[sig]
return re.sub(r'{{{ FTM_([\w\d_$]+) }}}', lambda m: fix(m), js) # masks[m.groups(0)[0]]
- funcs_js = function_table_maskize(funcs_js)
+ funcs_js = map(function_table_maskize, funcs_js)
else:
function_tables_defs = '\n'.join([table for table in last_forwarded_json['Functions']['tables'].itervalues()])
outfile.write(function_tables_defs)
- funcs_js = '''
+ funcs_js = ['''
// EMSCRIPTEN_START_FUNCS
-''' + funcs_js + '''
+'''] + funcs_js + ['''
// EMSCRIPTEN_END_FUNCS
-'''
+''']
- outfile.write(blockaddrsize(indexize(funcs_js)))
+ for funcs_js_item in funcs_js: # do this loop carefully to save memory
+ funcs_js_item = indexize(funcs_js_item)
+ funcs_js_item = blockaddrsize(funcs_js_item)
+ outfile.write(funcs_js_item)
funcs_js = None
outfile.write(indexize(post))
diff --git a/src/analyzer.js b/src/analyzer.js
index 926ac9d3..92b7d8cf 100644
--- a/src/analyzer.js
+++ b/src/analyzer.js
@@ -18,7 +18,7 @@ function recomputeLines(func) {
// Handy sets
var BRANCH_INVOKE = set('branch', 'invoke');
-var LABEL_ENDERS = set('branch', 'return');
+var LABEL_ENDERS = set('branch', 'return', 'switch');
var SIDE_EFFECT_CAUSERS = set('call', 'invoke', 'atomic');
var UNUNFOLDABLE = set('value', 'structvalue', 'type', 'phiparam');
@@ -653,13 +653,14 @@ function analyzer(data, sidePass) {
if (!isNumber(shifts)) {
// We can't statically legalize this, do the operation at runtime TODO: optimize
assert(sourceBits == 64, 'TODO: handle nonconstant shifts on != 64 bits');
+ assert(PRECISE_I64_MATH, 'Must have precise i64 math for non-constant 64-bit shifts');
+ Types.preciseI64MathUsed = 1;
value.intertype = 'value';
- value.ident = 'Runtime' + (ASM_JS ? '_' : '.') + 'bitshift64(' +
+ value.ident = 'var ' + value.assignTo + '$0 = _bitshift64' + value.op[0].toUpperCase() + value.op.substr(1) + '(' +
asmCoercion(sourceElements[0].ident, 'i32') + ',' +
asmCoercion(sourceElements[1].ident, 'i32') + ',' +
- Runtime['BITSHIFT64_' + value.op.toUpperCase()] + ',' +
asmCoercion(value.params[1].ident + '$0', 'i32') + ');' +
- 'var ' + value.assignTo + '$0 = ' + makeGetTempDouble(0, 'i32') + ', ' + value.assignTo + '$1 = ' + makeGetTempDouble(1, 'i32') + ';';
+ 'var ' + value.assignTo + '$1 = tempRet0;';
value.assignTo = null;
i++;
continue;
diff --git a/src/compiler.js b/src/compiler.js
index 447d34b7..bb72c7dd 100644
--- a/src/compiler.js
+++ b/src/compiler.js
@@ -141,8 +141,13 @@ if (phase == 'pre') {
if (settings_file) {
var settings = JSON.parse(read(settings_file));
- for (setting in settings) {
- eval(setting + ' = ' + JSON.stringify(settings[setting]));
+ for (key in settings) {
+ var value = settings[key];
+ if (value[0] == '@') {
+ // response file type thing, workaround for large inputs: value is @path-to-file
+ value = JSON.parse(read(value.substr(1)));
+ }
+ eval(key + ' = ' + JSON.stringify(value));
}
}
@@ -163,7 +168,7 @@ if (SAFE_HEAP >= 2) {
EXPORTED_FUNCTIONS = set(EXPORTED_FUNCTIONS);
EXPORTED_GLOBALS = set(EXPORTED_GLOBALS);
EXCEPTION_CATCHING_WHITELIST = set(EXCEPTION_CATCHING_WHITELIST);
-DEAD_FUNCTIONS = set(DEAD_FUNCTIONS);
+DEAD_FUNCTIONS = numberedSet(DEAD_FUNCTIONS);
RUNTIME_DEBUG = LIBRARY_DEBUG || GL_DEBUG;
diff --git a/src/headless.js b/src/headless.js
index 8e847d27..d81fb5a3 100644
--- a/src/headless.js
+++ b/src/headless.js
@@ -537,7 +537,7 @@ var document = {
case /* GL_MAX_FRAGMENT_UNIFORM_VECTORS */ 0x8DFD: return 4096;
case /* GL_MAX_VARYING_VECTORS */ 0x8DFC: return 32;
case /* GL_MAX_COMBINED_TEXTURE_IMAGE_UNITS */ 0x8B4D: return 32;
- default: throw 'getParameter ' + pname;
+ default: console.log('getParameter ' + pname + '?'); return 0;
}
},
getSupportedExtensions: function() {
@@ -686,6 +686,7 @@ var document = {
document.callEventListeners('pointerlockchange');
});
},
+ exitPointerLock: function(){},
style: {},
eventListeners: {},
addEventListener: document.addEventListener,
@@ -748,6 +749,8 @@ var document = {
body: {
appendChild: function(){},
},
+ exitPointerLock: function(){},
+ cancelFullScreen: function(){},
};
var alert = function(x) {
print(x);
diff --git a/src/jsifier.js b/src/jsifier.js
index d36f26ce..7db2ee70 100644
--- a/src/jsifier.js
+++ b/src/jsifier.js
@@ -397,6 +397,20 @@ function JSify(data, functionsOnly, givenFunctions) {
}
});
+ function processLibraryFunction(snippet, ident) {
+ snippet = snippet.toString();
+ assert(snippet.indexOf('XXX missing C define') == -1,
+ 'Trying to include a library function with missing C defines: ' + ident + ' | ' + snippet);
+
+ // name the function; overwrite if it's already named
+ snippet = snippet.replace(/function(?:\s+([^(]+))?\s*\(/, 'function _' + ident + '(');
+ if (LIBRARY_DEBUG) {
+ snippet = snippet.replace('{', '{ var ret = (function() { if (Runtime.debug) Module.printErr("[library call:' + ident + ': " + Array.prototype.slice.call(arguments).map(Runtime.prettyPrint) + "]"); ');
+ snippet = snippet.substr(0, snippet.length-1) + '}).apply(this, arguments); if (Runtime.debug && typeof ret !== "undefined") Module.printErr(" [ return:" + Runtime.prettyPrint(ret)); return ret; \n}';
+ }
+ return snippet;
+ }
+
// functionStub
substrate.addActor('FunctionStub', {
processItem: function(item) {
@@ -434,16 +448,7 @@ function JSify(data, functionsOnly, givenFunctions) {
snippet = stringifyWithFunctions(snippet);
} else if (typeof snippet === 'function') {
isFunction = true;
- snippet = snippet.toString();
- assert(snippet.indexOf('XXX missing C define') == -1,
- 'Trying to include a library function with missing C defines: ' + ident + ' | ' + snippet);
-
- // name the function; overwrite if it's already named
- snippet = snippet.replace(/function(?:\s+([^(]+))?\s*\(/, 'function _' + ident + '(');
- if (LIBRARY_DEBUG) {
- snippet = snippet.replace('{', '{ var ret = (function() { if (Runtime.debug) Module.printErr("[library call:' + ident + ': " + Array.prototype.slice.call(arguments).map(Runtime.prettyPrint) + "]"); ');
- snippet = snippet.substr(0, snippet.length-1) + '}).apply(this, arguments); if (Runtime.debug && typeof ret !== "undefined") Module.printErr(" [ return:" + Runtime.prettyPrint(ret)); return ret; \n}';
- }
+ snippet = processLibraryFunction(snippet, ident);
if (ASM_JS) Functions.libraryFunctions[ident] = 1;
}
@@ -507,9 +512,13 @@ function JSify(data, functionsOnly, givenFunctions) {
} else if (LibraryManager.library.hasOwnProperty(shortident)) {
item.JS = addFromLibrary(shortident);
} else if (!LibraryManager.library.hasOwnProperty(shortident + '__inline')) {
- item.JS = 'var ' + item.ident + '; // stub for ' + item.ident;
- if (WARN_ON_UNDEFINED_SYMBOLS || ASM_JS) { // always warn on undefs in asm, since it breaks validation
- warn('Unresolved symbol: ' + item.ident);
+ if (!(item.ident in DEAD_FUNCTIONS) && !UNRESOLVED_AS_DEAD) {
+ item.JS = 'var ' + item.ident + '; // stub for ' + item.ident;
+ if (ASM_JS) {
+ throw 'Unresolved symbol: ' + item.ident + ', this must be corrected for asm.js validation to succeed. Consider adding it to DEAD_FUNCTIONS.';
+ } else if (WARN_ON_UNDEFINED_SYMBOLS) {
+ warn('Unresolved symbol: ' + item.ident);
+ }
}
}
return ret;
@@ -717,6 +726,7 @@ function JSify(data, functionsOnly, givenFunctions) {
ret += indent + 'label = ' + getLabelId(block.entries[0]) + '; ' + (SHOW_LABELS ? '/* ' + getOriginalLabelId(block.entries[0]) + ' */' : '') + '\n';
} // otherwise, should have been set before!
if (func.setjmpTable) {
+ assert(!ASM_JS, 'asm.js mode does not support setjmp yet');
var setjmpTable = {};
ret += indent + 'var mySetjmpIds = {};\n';
ret += indent + 'var setjmpTable = {';
@@ -1316,6 +1326,7 @@ function JSify(data, functionsOnly, givenFunctions) {
} else {
callIdent = ident;
}
+ if (callIdent == '0') return 'abort(-2)';
var args = [];
var argsTypes = [];
@@ -1420,7 +1431,7 @@ function JSify(data, functionsOnly, givenFunctions) {
}
if (callIdent in DEAD_FUNCTIONS) {
- var ret = 'abort(7)';
+ var ret = 'abort(' + DEAD_FUNCTIONS[callIdent] + ')';
if (ASM_JS) ret = asmCoercion(ret, returnType);
return ret;
}
@@ -1563,16 +1574,25 @@ function JSify(data, functionsOnly, givenFunctions) {
// This is the main 'post' pass. Print out the generated code that we have here, together with the
// rest of the output that we started to print out earlier (see comment on the
// "Final shape that will be created").
- if (CORRUPTION_CHECK) {
- assert(!ASM_JS); // cannot monkeypatch asm!
- print(processMacros(read('corruptionCheck.js')));
- }
if (PRECISE_I64_MATH && Types.preciseI64MathUsed) {
+ if (!INCLUDE_FULL_LIBRARY) {
+ ['i64Add', 'bitshift64Shl', 'bitshift64Lshr', 'bitshift64Ashr'].forEach(function(func) {
+ print(processLibraryFunction(LibraryManager.library[func], func)); // must be first to be close to generated code
+ Functions.implementedFunctions['_' + func] = LibraryManager.library[func + '__sig'];
+ });
+ }
+ print('// EMSCRIPTEN_END_FUNCS\n');
print(read('long.js'));
} else {
+ print('// EMSCRIPTEN_END_FUNCS\n');
print('// Warning: printing of i64 values may be slightly rounded! No deep i64 math used, so precise i64 code not included');
print('var i64Math = null;');
}
+
+ if (CORRUPTION_CHECK) {
+ assert(!ASM_JS); // cannot monkeypatch asm!
+ print(processMacros(read('corruptionCheck.js')));
+ }
if (HEADLESS) {
print('if (!ENVIRONMENT_IS_WEB) {');
print(read('headless.js').replace("'%s'", "'http://emscripten.org'").replace("'?%s'", "''").replace('%s,', 'null,').replace('%d', '0'));
diff --git a/src/library.js b/src/library.js
index 3d00a4d5..d5f11cf3 100644
--- a/src/library.js
+++ b/src/library.js
@@ -504,7 +504,7 @@ LibraryManager.library = {
}
var utf8 = new Runtime.UTF8Processor();
function simpleOutput(val) {
- if (val === null || val === '\n'.charCodeAt(0)) {
+ if (val === null || val === {{{ charCode('\n') }}}) {
output.printer(output.buffer.join(''));
output.buffer = [];
} else {
@@ -600,8 +600,8 @@ LibraryManager.library = {
quit: function() {
if (!FS.init.initialized) return;
// Flush any partially-printed lines in stdout and stderr. Careful, they may have been closed
- if (FS.streams[2] && FS.streams[2].object.output.buffer.length > 0) FS.streams[2].object.output('\n'.charCodeAt(0));
- if (FS.streams[3] && FS.streams[3].object.output.buffer.length > 0) FS.streams[3].object.output('\n'.charCodeAt(0));
+ if (FS.streams[2] && FS.streams[2].object.output.buffer.length > 0) FS.streams[2].object.output({{{ charCode('\n') }}});
+ if (FS.streams[3] && FS.streams[3].object.output.buffer.length > 0) FS.streams[3].object.output({{{ charCode('\n') }}});
},
// Standardizes a path. Useful for making comparisons of pathnames work in a consistent manner.
@@ -828,11 +828,11 @@ LibraryManager.library = {
// Null or empty results in '.'.
var me = ___libgenSplitName;
if (!me.ret) {
- me.ret = allocate(['.'.charCodeAt(0), 0], 'i8', ALLOC_NORMAL);
+ me.ret = allocate([{{{ charCode('.') }}}, 0], 'i8', ALLOC_NORMAL);
}
return [me.ret, -1];
} else {
- var slash = '/'.charCodeAt(0);
+ var slash = {{{ charCode('/') }}};
var allSlashes = true;
var slashPositions = [];
for (var i = 0; {{{ makeGetValue('path', 'i', 'i8') }}} !== 0; i++) {
@@ -1730,7 +1730,12 @@ LibraryManager.library = {
}
var contents = stream.object.contents;
var size = Math.min(contents.length - offset, nbyte);
- if (contents.subarray || contents.slice) { // typed array or normal array
+#if USE_TYPED_ARRAYS == 2
+ if (contents.subarray) { // typed array
+ HEAPU8.set(contents.subarray(offset, offset+size), buf);
+ } else
+#endif
+ if (contents.slice) { // normal array
for (var i = 0; i < size; i++) {
{{{ makeSetValue('buf', 'i', 'contents[offset + i]', 'i8') }}}
}
@@ -2452,9 +2457,9 @@ LibraryManager.library = {
_scanString: function(format, get, unget, varargs) {
if (!__scanString.whiteSpace) {
__scanString.whiteSpace = {};
- __scanString.whiteSpace[' '.charCodeAt(0)] = 1;
- __scanString.whiteSpace['\t'.charCodeAt(0)] = 1;
- __scanString.whiteSpace['\n'.charCodeAt(0)] = 1;
+ __scanString.whiteSpace[{{{ charCode(' ') }}}] = 1;
+ __scanString.whiteSpace[{{{ charCode('\t') }}}] = 1;
+ __scanString.whiteSpace[{{{ charCode('\n') }}}] = 1;
__scanString.whiteSpace[' '] = 1;
__scanString.whiteSpace['\t'] = 1;
__scanString.whiteSpace['\n'] = 1;
@@ -2514,8 +2519,8 @@ LibraryManager.library = {
if (format[formatIndex] === '%') {
formatIndex++;
var maxSpecifierStart = formatIndex;
- while (format[formatIndex].charCodeAt(0) >= '0'.charCodeAt(0) &&
- format[formatIndex].charCodeAt(0) <= '9'.charCodeAt(0)) {
+ while (format[formatIndex].charCodeAt(0) >= {{{ charCode('0') }}} &&
+ format[formatIndex].charCodeAt(0) <= {{{ charCode('9') }}}) {
formatIndex++;
}
var max_;
@@ -2561,11 +2566,11 @@ LibraryManager.library = {
while ((curr < max_ || isNaN(max_)) && next > 0) {
if (!(next in __scanString.whiteSpace) && // stop on whitespace
(type == 's' ||
- ((type === 'd' || type == 'u' || type == 'i') && ((next >= '0'.charCodeAt(0) && next <= '9'.charCodeAt(0)) ||
- (first && next == '-'.charCodeAt(0)))) ||
- (type === 'x' && (next >= '0'.charCodeAt(0) && next <= '9'.charCodeAt(0) ||
- next >= 'a'.charCodeAt(0) && next <= 'f'.charCodeAt(0) ||
- next >= 'A'.charCodeAt(0) && next <= 'F'.charCodeAt(0)))) &&
+ ((type === 'd' || type == 'u' || type == 'i') && ((next >= {{{ charCode('0') }}} && next <= {{{ charCode('9') }}}) ||
+ (first && next == {{{ charCode('-') }}}))) ||
+ (type === 'x' && (next >= {{{ charCode('0') }}} && next <= {{{ charCode('9') }}} ||
+ next >= {{{ charCode('a') }}} && next <= {{{ charCode('f') }}} ||
+ next >= {{{ charCode('A') }}} && next <= {{{ charCode('F') }}}))) &&
(formatIndex >= format.length || next !== format[formatIndex].charCodeAt(0))) { // Stop when we read something that is coming up
buffer.push(String.fromCharCode(next));
next = get();
@@ -2633,7 +2638,7 @@ LibraryManager.library = {
}
return fields;
},
- // Performs prtinf-style formatting.
+ // Performs printf-style formatting.
// format: A pointer to the format string.
// varargs: A pointer to the start of the arguments list.
// Returns the resulting string string as a character array.
@@ -2670,7 +2675,7 @@ LibraryManager.library = {
curr = {{{ makeGetValue(0, 'textIndex', 'i8') }}};
if (curr === 0) break;
next = {{{ makeGetValue(0, 'textIndex+1', 'i8') }}};
- if (curr == '%'.charCodeAt(0)) {
+ if (curr == {{{ charCode('%') }}}) {
// Handle flags.
var flagAlwaysSigned = false;
var flagLeftAlign = false;
@@ -2678,16 +2683,16 @@ LibraryManager.library = {
var flagZeroPad = false;
flagsLoop: while (1) {
switch (next) {
- case '+'.charCodeAt(0):
+ case {{{ charCode('+') }}}:
flagAlwaysSigned = true;
break;
- case '-'.charCodeAt(0):
+ case {{{ charCode('-') }}}:
flagLeftAlign = true;
break;
- case '#'.charCodeAt(0):
+ case {{{ charCode('#') }}}:
flagAlternative = true;
break;
- case '0'.charCodeAt(0):
+ case {{{ charCode('0') }}}:
if (flagZeroPad) {
break flagsLoop;
} else {
@@ -2703,13 +2708,13 @@ LibraryManager.library = {
// Handle width.
var width = 0;
- if (next == '*'.charCodeAt(0)) {
+ if (next == {{{ charCode('*') }}}) {
width = getNextArg('i32');
textIndex++;
next = {{{ makeGetValue(0, 'textIndex+1', 'i8') }}};
} else {
- while (next >= '0'.charCodeAt(0) && next <= '9'.charCodeAt(0)) {
- width = width * 10 + (next - '0'.charCodeAt(0));
+ while (next >= {{{ charCode('0') }}} && next <= {{{ charCode('9') }}}) {
+ width = width * 10 + (next - {{{ charCode('0') }}});
textIndex++;
next = {{{ makeGetValue(0, 'textIndex+1', 'i8') }}};
}
@@ -2717,20 +2722,20 @@ LibraryManager.library = {
// Handle precision.
var precisionSet = false;
- if (next == '.'.charCodeAt(0)) {
+ if (next == {{{ charCode('.') }}}) {
var precision = 0;
precisionSet = true;
textIndex++;
next = {{{ makeGetValue(0, 'textIndex+1', 'i8') }}};
- if (next == '*'.charCodeAt(0)) {
+ if (next == {{{ charCode('*') }}}) {
precision = getNextArg('i32');
textIndex++;
} else {
while(1) {
var precisionChr = {{{ makeGetValue(0, 'textIndex+1', 'i8') }}};
- if (precisionChr < '0'.charCodeAt(0) ||
- precisionChr > '9'.charCodeAt(0)) break;
- precision = precision * 10 + (precisionChr - '0'.charCodeAt(0));
+ if (precisionChr < {{{ charCode('0') }}} ||
+ precisionChr > {{{ charCode('9') }}}) break;
+ precision = precision * 10 + (precisionChr - {{{ charCode('0') }}});
textIndex++;
}
}
@@ -2744,7 +2749,7 @@ LibraryManager.library = {
switch (String.fromCharCode(next)) {
case 'h':
var nextNext = {{{ makeGetValue(0, 'textIndex+2', 'i8') }}};
- if (nextNext == 'h'.charCodeAt(0)) {
+ if (nextNext == {{{ charCode('h') }}}) {
textIndex++;
argSize = 1; // char (actually i32 in varargs)
} else {
@@ -2753,7 +2758,7 @@ LibraryManager.library = {
break;
case 'l':
var nextNext = {{{ makeGetValue(0, 'textIndex+2', 'i8') }}};
- if (nextNext =