diff options
author | Alon Zakai <alonzakai@gmail.com> | 2011-12-03 11:54:08 -0800 |
---|---|---|
committer | Alon Zakai <alonzakai@gmail.com> | 2011-12-03 11:54:08 -0800 |
commit | 4bf23981037b66af07ddf9ee9b089a9f2b62b2a1 (patch) | |
tree | 738138a0078db1c3e6c6d3a9b421d99bfccaa946 | |
parent | 1fbe97bff634539433074c8156a82c2dee67399a (diff) |
refactoring towards supporting node.js
-rw-r--r-- | settings.py | 3 | ||||
-rw-r--r-- | src/analyzer.js | 10 | ||||
-rw-r--r-- | src/compiler.js | 44 | ||||
-rw-r--r-- | src/jsifier.js | 18 | ||||
-rw-r--r-- | src/library.js | 24 | ||||
-rw-r--r-- | src/modules.js | 2 | ||||
-rw-r--r-- | src/parseTools.js | 57 | ||||
-rw-r--r-- | src/postamble.js | 2 | ||||
-rw-r--r-- | src/runtime.js | 44 |
9 files changed, 112 insertions, 92 deletions
diff --git a/settings.py b/settings.py index f4483921..b294f8bd 100644 --- a/settings.py +++ b/settings.py @@ -11,9 +11,11 @@ COMPILER_OPTS = [] SPIDERMONKEY_ENGINE = [os.path.expanduser('~/Dev/mozilla-central/js/src/js'), '-m', '-n'] V8_ENGINE = [os.path.expanduser('~/Dev/v8/d8')] +NODE_JS = 'node' #COMPILER_ENGINE=SPIDERMONKEY_ENGINE COMPILER_ENGINE=V8_ENGINE +#COMPILER_ENGINE=[NODE_JS] JS_ENGINE=V8_ENGINE @@ -22,5 +24,4 @@ TIMEOUT = None # Tools CLOSURE_COMPILER = os.path.expanduser('~/Dev/closure-compiler/compiler.jar') -NODE_JS = 'node' diff --git a/src/analyzer.js b/src/analyzer.js index dfb11e90..5b34c665 100644 --- a/src/analyzer.js +++ b/src/analyzer.js @@ -231,9 +231,9 @@ function analyzer(data) { Types.flipTypes(); // Fake a quantum size of 4 for fat types. TODO: Might want non-4 for some reason? var trueQuantumSize = QUANTUM_SIZE; - QUANTUM_SIZE = 4; + Runtime.QUANTUM_SIZE = 4; analyzeTypes(item, true); - QUANTUM_SIZE = trueQuantumSize; + Runtime.QUANTUM_SIZE = trueQuantumSize; Types.flipTypes(); } @@ -474,11 +474,11 @@ function analyzer(data) { function getSize(types, type, fat) { if (types[type]) return types[type].flatSize; if (fat) { - QUANTUM_SIZE = 4; + Runtime.QUANTUM_SIZE = 4; } - var ret = getNativeTypeSize(type); + var ret = Runtime.getNativeTypeSize(type); if (fat) { - QUANTUM_SIZE = 1; + Runtime.QUANTUM_SIZE = 1; } return ret; } diff --git a/src/compiler.js b/src/compiler.js index 32c1120e..ea55d95e 100644 --- a/src/compiler.js +++ b/src/compiler.js @@ -8,11 +8,30 @@ try { } catch(e) {} var arguments_ = []; -var globalScope = this; -var ENVIRONMENT_IS_SHELL = typeof window === 'undefined'; +var ENVIRONMENT_IS_NODE = typeof process === 'object'; +var ENVIRONMENT_IS_WEB = typeof window === 'object'; +var ENVIRONMENT_IS_SHELL = !ENVIRONMENT_IS_WEB && !ENVIRONMENT_IS_NODE; -if (ENVIRONMENT_IS_SHELL) { +if (ENVIRONMENT_IS_NODE) { + // Expose functionality in the same simple way that the shells work + print = function(x) { + process.stdout.write(x + '\n'); + }; + printErr = function(x) { + process.stderr.write(x + '\n'); + }; + + var nodeFS = require('fs'); + + read = function(filename) { + if (filename[0] != '/') filename = __dirname.split('/').slice(0, -1).join('/') + '/src/' + filename; + return nodeFS.readFileSync(filename).toString(); + }; + + arguments_ = process.argv.slice(2); + +} else if (ENVIRONMENT_IS_SHELL) { // Polyfill over SpiderMonkey/V8 differences if (!this['read']) { read = function(f) { snarf(f) }; @@ -23,8 +42,8 @@ if (ENVIRONMENT_IS_SHELL) { } else { arguments_ = arguments; } -} else { - // We are on the web. + +} else if (ENVIRONMENT_IS_WEB) { printErr = function(x) { console.log(x); }; @@ -39,11 +58,17 @@ if (ENVIRONMENT_IS_SHELL) { if (this['arguments']) { arguments_ = arguments; } +} else { + throw 'Unknown runtime environment. Where are we?'; +} + +function globalEval(x) { + eval.call(null, x); } if (!this['load']) { load = function(f) { - eval.call(globalScope, read(f)); + globalEval(read(f)); }; } @@ -61,12 +86,10 @@ var ll_file = arguments_[1]; if (settings_file) { var settings = JSON.parse(read(settings_file)); for (setting in settings) { - this[setting] = settings[setting]; + eval(setting + ' = ' + JSON.stringify(settings[setting])); } } -var CONSTANTS = { 'QUANTUM_SIZE': QUANTUM_SIZE }; - if (CORRECT_SIGNS >= 2) { CORRECT_SIGNS_LINES = set(CORRECT_SIGNS_LINES); // for fast checking } @@ -114,7 +137,8 @@ load('parseTools.js'); load('intertyper.js'); load('analyzer.js'); load('jsifier.js'); -eval.call(globalScope, processMacros(preprocess(read('runtime.js')))); +globalEval(processMacros(preprocess(read('runtime.js')))); +Runtime.QUANTUM_SIZE = QUANTUM_SIZE; //=============================== // Main diff --git a/src/jsifier.js b/src/jsifier.js index e138f6f4..2cb4dee9 100644 --- a/src/jsifier.js +++ b/src/jsifier.js @@ -31,7 +31,7 @@ function JSify(data, functionsOnly, givenFunctions) { var shellParts = read(shellFile).split('{{BODY}}'); print(shellParts[0]); var preFile = BUILD_AS_SHARED_LIB ? 'preamble_sharedlib.js' : 'preamble.js'; - var pre = processMacros(preprocess(read(preFile).replace('{{RUNTIME}}', getRuntime()), CONSTANTS)); + var pre = processMacros(preprocess(read(preFile).replace('{{RUNTIME}}', getRuntime()))); print(pre); print('Runtime.QUANTUM_SIZE = ' + QUANTUM_SIZE); @@ -266,7 +266,7 @@ function JSify(data, functionsOnly, givenFunctions) { var val = LibraryManager.library[shortident]; var padding; if (Runtime.isNumberType(item.type) || isPointerType(item.type)) { - padding = [item.type].concat(zeros(getNativeFieldSize(item.type))); + padding = [item.type].concat(zeros(Runtime.getNativeFieldSize(item.type))); } else { padding = makeEmptyStruct(item.type); } @@ -985,20 +985,20 @@ function JSify(data, functionsOnly, givenFunctions) { } else { if (!(param.type == 'i64' && I64_MODE == 1)) { varargs.push(val); - varargs = varargs.concat(zeros(getNativeFieldSize(param.type)-1)); + varargs = varargs.concat(zeros(Runtime.getNativeFieldSize(param.type)-1)); varargsTypes.push(param.type); - varargsTypes = varargsTypes.concat(zeros(getNativeFieldSize(param.type)-1)); + varargsTypes = varargsTypes.concat(zeros(Runtime.getNativeFieldSize(param.type)-1)); } else { // i64 mode 1. Write one i32 with type i64, and one i32 with type i32 varargs.push(val + '[0]'); - varargs = varargs.concat(zeros(getNativeFieldSize('i32')-1)); + varargs = varargs.concat(zeros(Runtime.getNativeFieldSize('i32')-1)); ignoreFunctionIndexizing.push(varargs.length); // We will have a value there, but no type (the type is i64, but we write two i32s) varargs.push(val + '[1]'); - varargs = varargs.concat(zeros(getNativeFieldSize('i32')-1)); + varargs = varargs.concat(zeros(Runtime.getNativeFieldSize('i32')-1)); varargsTypes.push('i64'); - varargsTypes = varargsTypes.concat(zeros(getNativeFieldSize('i32')-1)); + varargsTypes = varargsTypes.concat(zeros(Runtime.getNativeFieldSize('i32')-1)); varargsTypes.push('i32'); - varargsTypes = varargsTypes.concat(zeros(getNativeFieldSize('i32')-1)); + varargsTypes = varargsTypes.concat(zeros(Runtime.getNativeFieldSize('i32')-1)); } } }); @@ -1098,7 +1098,7 @@ function JSify(data, functionsOnly, givenFunctions) { print('Runtime.structMetadata = ' + JSON.stringify(Types.structMetadata)); } var postFile = BUILD_AS_SHARED_LIB ? 'postamble_sharedlib.js' : 'postamble.js'; - var postParts = processMacros(preprocess(read(postFile), CONSTANTS)).split('{{GLOBAL_VARS}}'); + var postParts = processMacros(preprocess(read(postFile))).split('{{GLOBAL_VARS}}'); print(postParts[0]); // Print out global variables and postsets TODO: batching diff --git a/src/library.js b/src/library.js index 1f63e6d0..ce6152d1 100644 --- a/src/library.js +++ b/src/library.js @@ -388,7 +388,7 @@ LibraryManager.library = { FS.streams[_stdout] = FS.streams[2]; FS.streams[_stderr] = FS.streams[3]; __impure_ptr = allocate([ allocate( - {{{ QUANTUM_SIZE === 4 ? '[0, 0, 0, 0, _stdin, 0, 0, 0, _stdout, 0, 0, 0, _stderr, 0, 0, 0]' : '[0, _stdin, _stdout, _stderr]' }}}, + {{{ Runtime.QUANTUM_SIZE === 4 ? '[0, 0, 0, 0, _stdin, 0, 0, 0, _stdout, 0, 0, 0, _stderr, 0, 0, 0]' : '[0, _stdin, _stdout, _stderr]' }}}, 'void*', ALLOC_STATIC) ], 'void*', ALLOC_STATIC); }, @@ -3424,7 +3424,7 @@ LibraryManager.library = { ENV['_'] = './this.program'; // Allocate memory. poolPtr = allocate(TOTAL_ENV_SIZE, 'i8', ALLOC_STATIC); - envPtr = allocate(MAX_ENV_VALUES * {{{ QUANTUM_SIZE }}}, + envPtr = allocate(MAX_ENV_VALUES * {{{ Runtime.QUANTUM_SIZE }}}, 'i8*', ALLOC_STATIC); {{{ makeSetValue('envPtr', '0', 'poolPtr', 'i8*') }}} _environ = allocate([envPtr], 'i8**', ALLOC_STATIC); @@ -3609,14 +3609,14 @@ LibraryManager.library = { memcpy__inline: function (dest, src, num, idunno) { var ret = ''; #if ASSERTIONS - ret += "assert(" + num + " % 1 === 0, 'memcpy given ' + " + num + " + ' bytes to copy. Problem with QUANTUM_SIZE=1 corrections perhaps?');"; + ret += "assert(" + num + " % 1 === 0, 'memcpy given ' + " + num + " + ' bytes to copy. Problem with quantum=1 corrections perhaps?');"; #endif ret += makeCopyValues(dest, src, num, 'null'); return ret; }, memcpy: function (dest, src, num, idunno) { #if ASSERTIONS - assert(num % 1 === 0, 'memcpy given ' + num + ' bytes to copy. Problem with QUANTUM_SIZE=1 corrections perhaps?'); + assert(num % 1 === 0, 'memcpy given ' + num + ' bytes to copy. Problem with quantum=1 corrections perhaps?'); #endif {{{ makeCopyValues('dest', 'src', 'num', 'null') }}}; }, @@ -4032,7 +4032,7 @@ LibraryManager.library = { llvm_va_end: function() {}, llvm_va_copy: function(ppdest, ppsrc) { - {{{ makeCopyValues('ppdest', 'ppsrc', QUANTUM_SIZE, 'null') }}} + {{{ makeCopyValues('ppdest', 'ppsrc', Runtime.QUANTUM_SIZE, 'null') }}} /* Alternate implementation that copies the actual DATA; it assumes the va_list is prefixed by its size var psrc = IHEAP[ppsrc]-1; var num = IHEAP[psrc]; // right before the data, is the number of (flattened) values @@ -4088,15 +4088,15 @@ LibraryManager.library = { __dynamic_cast: function(ptr, knownTI, attemptedTI, idunno) { var ptrTV = {{{ makeGetValue('ptr', '0', '*') }}}; var count = {{{ makeGetValue('ptrTV', '0', '*') }}}; - ptrTV -= {{{ QUANTUM_SIZE }}}; + ptrTV -= {{{ Runtime.QUANTUM_SIZE }}}; var TI = {{{ makeGetValue('ptrTV', '0', '*') }}}; do { if (TI == attemptedTI) return 1; // Go to parent class - var type_infoAddr = {{{ makeGetValue('TI', '0', '*') }}} - {{{ QUANTUM_SIZE*2 }}}; + var type_infoAddr = {{{ makeGetValue('TI', '0', '*') }}} - {{{ Runtime.QUANTUM_SIZE*2 }}}; var type_info = {{{ makeGetValue('type_infoAddr', '0', '*') }}}; if (type_info == 1) return 0; // no parent class - var TIAddr = TI + {{{ QUANTUM_SIZE*2 }}}; + var TIAddr = TI + {{{ Runtime.QUANTUM_SIZE*2 }}}; var TI = {{{ makeGetValue('TIAddr', '0', '*') }}}; } while (1); @@ -4851,10 +4851,10 @@ LibraryManager.library = { // TODO: Use (malleable) environment variables instead of system settings. if (__tzname) return; // glibc does not need the double __ - __timezone = _malloc(QUANTUM_SIZE); + __timezone = _malloc({{{ Runtime.QUANTUM_SIZE }}}); {{{ makeSetValue('__timezone', '0', '-(new Date()).getTimezoneOffset() * 60', 'i32') }}} - __daylight = _malloc(QUANTUM_SIZE); + __daylight = _malloc({{{ Runtime.QUANTUM_SIZE }}}); var winter = new Date(2000, 0, 1); var summer = new Date(2000, 6, 1); {{{ makeSetValue('__daylight', '0', 'Number(winter.getTimezoneOffset() != summer.getTimezoneOffset())', 'i32') }}} @@ -4863,9 +4863,9 @@ LibraryManager.library = { var summerName = summer.toString().match(/\(([A-Z]+)\)/)[1]; var winterNamePtr = allocate(intArrayFromString(winterName), 'i8', ALLOC_NORMAL); var summerNamePtr = allocate(intArrayFromString(summerName), 'i8', ALLOC_NORMAL); - __tzname = _malloc(2 * QUANTUM_SIZE); // glibc does not need the double __ + __tzname = _malloc(2 * {{{ Runtime.QUANTUM_SIZE }}}); // glibc does not need the double __ {{{ makeSetValue('__tzname', '0', 'winterNamePtr', 'i32') }}} - {{{ makeSetValue('__tzname', QUANTUM_SIZE, 'summerNamePtr', 'i32') }}} + {{{ makeSetValue('__tzname', Runtime.QUANTUM_SIZE, 'summerNamePtr', 'i32') }}} }, stime__deps: ['$ERRNO_CODES', '__setErrNo'], diff --git a/src/modules.js b/src/modules.js index bf1c0a7d..02a1f102 100644 --- a/src/modules.js +++ b/src/modules.js @@ -269,7 +269,7 @@ var LibraryManager = { assert(!this.library); for (var suffix in set('', '_sdl', '_browser')) { - eval(processMacros(preprocess(read('library' + suffix + '.js'), CONSTANTS))); + eval(processMacros(preprocess(read('library' + suffix + '.js')))); } }, diff --git a/src/parseTools.js b/src/parseTools.js index 13f52ced..800d6b8b 100644 --- a/src/parseTools.js +++ b/src/parseTools.js @@ -15,11 +15,8 @@ function processMacros(text) { } // Simple #if/else/endif preprocessing for a file. Checks if the -// ident checked is true in our global. Also replaces some constants. -function preprocess(text, constants) { - for (var constant in constants) { - text = text.replace(eval('/' + constant + '/g'), constants[constant]); - } +// ident checked is true in our global. +function preprocess(text) { var lines = text.split('\n'); var ret = ''; var showStack = []; @@ -734,32 +731,6 @@ function getLabelIds(labels) { return labels.map(function(label) { return label.ident }); } -//! Returns the size of a type, as C/C++ would have it (in 32-bit, for now), in bytes. -//! @param type The type, by name. -function getNativeTypeSize(type) { - if (QUANTUM_SIZE == 1) return 1; - var size = { - '%i1': 1, - '%i8': 1, - '%i16': 2, - '%i32': 4, - '%i64': 8, - "%float": 4, - "%double": 8 - }['%'+type]; // add '%' since float and double confuse Closure compiler as keys, and also spidermonkey as a compiler will remove 's from '_i8' etc - if (!size && type[type.length-1] == '*') { - size = QUANTUM_SIZE; // A pointer - } - return size; -} - -//! Returns the size of a structure field, as C/C++ would have it (in 32-bit, -//! for now). -//! @param type The type, by name. -function getNativeFieldSize(type) { - return Math.max(Runtime.getNativeTypeSize(type), QUANTUM_SIZE); -} - function cleanLabel(label) { if (label[0] == 'B') { return label.substr(5); @@ -777,7 +748,7 @@ function calcAllocatedSize(type) { if (pointingLevels(type) == 0 && isStructType(type)) { return Types.types[type].flatSize; // makeEmptyStruct(item.allocatedType).length; } else { - return getNativeTypeSize(type); // We can really get away with '1', though, at least on the stack... + return Runtime.getNativeTypeSize(type); // We can really get away with '1', though, at least on the stack... } } @@ -789,7 +760,7 @@ function generateStructTypes(type) { if (I64_MODE == 1 && type == 'i64') { return ['i64', 0, 0, 0, 'i32', 0, 0, 0]; } - return [type].concat(zeros(getNativeFieldSize(type))); + return [type].concat(zeros(Runtime.getNativeFieldSize(type))); } // Avoid multiple concats by finding the size first. This is much faster @@ -904,10 +875,10 @@ function getHeapOffset(offset, type) { if (USE_TYPED_ARRAYS !== 2) { return offset; } else { - if (getNativeFieldSize(type) > 4) { + if (Runtime.getNativeFieldSize(type) > 4) { type = 'i32'; // XXX we emulate 64-bit values as 32 } - var shifts = Math.log(getNativeTypeSize(type))/Math.LN2; + var shifts = Math.log(Runtime.getNativeTypeSize(type))/Math.LN2; if (shifts != 0) { return '((' + offset + ')>>' + (shifts) + ')'; } else { @@ -929,7 +900,7 @@ function makeGetValue(ptr, pos, type, noNeedFirst, unsigned, ignore, align) { if (EMULATE_UNALIGNED_ACCESSES && USE_TYPED_ARRAYS == 2 && align && isIntImplemented(type)) { // TODO: support unaligned doubles and floats // Alignment is important here. May need to split this up - var bytes = getNativeTypeSize(type); + var bytes = Runtime.getNativeTypeSize(type); if (bytes > align) { var ret = '/* unaligned */('; if (bytes <= 4) { @@ -942,7 +913,7 @@ function makeGetValue(ptr, pos, type, noNeedFirst, unsigned, ignore, align) { } else { assert(bytes == 8); ret += 'tempBigInt=' + makeGetValue(ptr, pos, 'i32', noNeedFirst, true, ignore, align) + ','; - ret += 'tempBigInt2=' + makeGetValue(ptr, getFastValue(pos, '+', getNativeTypeSize('i32')), 'i32', noNeedFirst, true, ignore, align) + ','; + ret += 'tempBigInt2=' + makeGetValue(ptr, getFastValue(pos, '+', Runtime.getNativeTypeSize('i32')), 'i32', noNeedFirst, true, ignore, align) + ','; ret += makeI64('tempBigInt', 'tempBigInt2'); } ret += ')'; @@ -952,7 +923,7 @@ function makeGetValue(ptr, pos, type, noNeedFirst, unsigned, ignore, align) { if (type == 'i64' && I64_MODE == 1) { return '[' + makeGetValue(ptr, pos, 'i32', noNeedFirst, unsigned, ignore) + ',' - + makeGetValue(ptr, getFastValue(pos, '+', getNativeTypeSize('i32')), 'i32', noNeedFirst, unsigned, ignore) + ']'; + + makeGetValue(ptr, getFastValue(pos, '+', Runtime.getNativeTypeSize('i32')), 'i32', noNeedFirst, unsigned, ignore) + ']'; } var offset = calcFastOffset(ptr, pos, noNeedFirst); @@ -1005,7 +976,7 @@ function makeSetValue(ptr, pos, value, type, noNeedFirst, ignore, align) { if (EMULATE_UNALIGNED_ACCESSES && USE_TYPED_ARRAYS == 2 && align && isIntImplemented(type)) { // TODO: support unaligned doubles and floats // Alignment is important here. May need to split this up - var bytes = getNativeTypeSize(type); + var bytes = Runtime.getNativeTypeSize(type); if (bytes > align) { var ret = '/* unaligned */'; if (bytes <= 4) { @@ -1018,7 +989,7 @@ function makeSetValue(ptr, pos, value, type, noNeedFirst, ignore, align) { assert(bytes == 8); ret += 'tempPair=' + ensureI64_1(value) + ';'; ret += makeSetValue(ptr, pos, 'tempPair[0]', 'i32', noNeedFirst, ignore, align) + ';'; - ret += makeSetValue(ptr, getFastValue(pos, '+', getNativeTypeSize('i32')), 'tempPair[1]', 'i32', noNeedFirst, ignore, align) + ';'; + ret += makeSetValue(ptr, getFastValue(pos, '+', Runtime.getNativeTypeSize('i32')), 'tempPair[1]', 'i32', noNeedFirst, ignore, align) + ';'; } return ret; } @@ -1026,7 +997,7 @@ function makeSetValue(ptr, pos, value, type, noNeedFirst, ignore, align) { if (type == 'i64' && I64_MODE == 1) { return '(' + makeSetValue(ptr, pos, value + '[0]', 'i32', noNeedFirst, ignore) + ',' - + makeSetValue(ptr, getFastValue(pos, '+', getNativeTypeSize('i32')), value + '[1]', 'i32', noNeedFirst, ignore) + ')'; + + makeSetValue(ptr, getFastValue(pos, '+', Runtime.getNativeTypeSize('i32')), value + '[1]', 'i32', noNeedFirst, ignore) + ')'; } value = indexizeFunctions(value, type); @@ -1184,7 +1155,7 @@ function getFastValue(a, op, b, type) { return b; } else if (b == 1) { return a; - } else if (isNumber(b) && type && isIntImplemented(type) && getNativeTypeSize(type) <= 32) { + } else if (isNumber(b) && type && isIntImplemented(type) && Runtime.getNativeTypeSize(type) <= 32) { var shifts = Math.log(parseFloat(b))/Math.LN2; if (shifts % 1 == 0) { return '(' + a + '<<' + shifts + ')'; @@ -1379,7 +1350,7 @@ function getGetElementPtrIndexes(item) { if (isStructType(type)) { indexes.push(getFastValue(Types.types[type].flatSize, '*', offset, 'i32')); } else { - indexes.push(getFastValue(getNativeTypeSize(type), '*', offset, 'i32')); + indexes.push(getFastValue(Runtime.getNativeTypeSize(type), '*', offset, 'i32')); } } item.params.slice(2, item.params.length).forEach(function(arg) { diff --git a/src/postamble.js b/src/postamble.js index 51ffc6ee..0e295171 100644 --- a/src/postamble.js +++ b/src/postamble.js @@ -4,7 +4,7 @@ Module.callMain = function callMain(args) { var argc = args.length+1; function pad() { - for (var i = 0; i < QUANTUM_SIZE-1; i++) { + for (var i = 0; i < {{{ QUANTUM_SIZE }}}-1; i++) { argv.push(0); } } diff --git a/src/runtime.js b/src/runtime.js index 7e28b08e..a6261c74 100644 --- a/src/runtime.js +++ b/src/runtime.js @@ -16,15 +16,15 @@ var RuntimeGenerator = { ret += '; _memset(' + type + 'TOP, 0, ' + size + ')'; } ret += '; ' + type + 'TOP += ' + size; - if (QUANTUM_SIZE > 1) { - ret += ';' + RuntimeGenerator.alignMemory(type + 'TOP', QUANTUM_SIZE); + if ({{{ QUANTUM_SIZE }}} > 1) { + ret += ';' + RuntimeGenerator.alignMemory(type + 'TOP', {{{ QUANTUM_SIZE }}}); } return ret; }, // An allocation that lives as long as the current function call stackAlloc: function(size) { - if (USE_TYPED_ARRAYS === 2) 'STACKTOP += STACKTOP % ' + (QUANTUM_SIZE - (isNumber(size) ? Math.min(size, QUANTUM_SIZE) : QUANTUM_SIZE)) + ';'; + if (USE_TYPED_ARRAYS === 2) 'STACKTOP += STACKTOP % ' + ({{{ QUANTUM_SIZE }}} - (isNumber(size) ? Math.min(size, {{{ QUANTUM_SIZE }}}) : {{{ QUANTUM_SIZE }}})) + ';'; var ret = RuntimeGenerator.alloc(size, 'STACK', INIT_STACK); if (ASSERTIONS) { ret += '; assert(STACKTOP < STACK_ROOT + STACK_MAX, "Ran out of stack")'; @@ -61,15 +61,15 @@ var RuntimeGenerator = { alignMemory: function(target, quantum) { if (typeof quantum !== 'number') { - quantum = '(quantum ? quantum : QUANTUM_SIZE)'; + quantum = '(quantum ? quantum : {{{ QUANTUM_SIZE }}})'; } return target + ' = ' + Runtime.forceAlign(target, quantum) + ';'; } }; function unInline(name_, params) { - var src = '(function ' + name_ + '(' + params + ') { var ret = ' + RuntimeGenerator[name_].apply(globalScope, params) + '; return ret; })'; - var ret = eval.call(globalScope, src); + var src = '(function ' + name_ + '(' + params + ') { var ret = ' + RuntimeGenerator[name_].apply(null, params) + '; return ret; })'; + var ret = eval(src); return ret; } @@ -82,7 +82,7 @@ var Runtime = { }, forceAlign: function(target, quantum) { - quantum = quantum || QUANTUM_SIZE; + quantum = quantum || {{{ QUANTUM_SIZE }}}; if (isNumber(target) && isNumber(quantum)) { return Math.ceil(target/quantum)*quantum; } else { @@ -116,8 +116,32 @@ var Runtime = { return l + h; }, - getNativeFieldSize: getNativeFieldSize, - getNativeTypeSize: getNativeTypeSize, + //! Returns the size of a type, as C/C++ would have it (in 32-bit, for now), in bytes. + //! @param type The type, by name. + getNativeTypeSize: function(type, quantumSize) { + if (Runtime.QUANTUM_SIZE == 1) return 1; + var size = { + '%i1': 1, + '%i8': 1, + '%i16': 2, + '%i32': 4, + '%i64': 8, + "%float": 4, + "%double": 8 + }['%'+type]; // add '%' since float and double confuse Closure compiler as keys, and also spidermonkey as a compiler will remove 's from '_i8' etc + if (!size && type[type.length-1] == '*') { + size = Runtime.QUANTUM_SIZE; // A pointer + } + return size; + }, + + //! Returns the size of a structure field, as C/C++ would have it (in 32-bit, + //! for now). + //! @param type The type, by name. + getNativeFieldSize: function(type) { + return Math.max(Runtime.getNativeTypeSize(type), Runtime.QUANTUM_SIZE); + }, + dedup: dedup, set: set, @@ -141,7 +165,7 @@ var Runtime = { } else { throw 'Unclear type in struct: ' + field + ', in ' + type.name_ + ' :: ' + dump(Types.types[type.name_]); } - alignSize = type.packed ? 1 : Math.min(alignSize, QUANTUM_SIZE); + alignSize = type.packed ? 1 : Math.min(alignSize, Runtime.QUANTUM_SIZE); type.alignSize = Math.max(type.alignSize, alignSize); var curr = Runtime.alignMemory(type.flatSize, alignSize); // if necessary, place this on aligned memory type.flatSize = curr + size; |