Implement reference counting (#592)

This commit is contained in:
Daniel Wirtz
2019-06-05 23:15:39 +02:00
committed by GitHub
parent 3ed76a97f0
commit 0484a6b740
601 changed files with 261645 additions and 146131 deletions

View File

@ -22,6 +22,8 @@ const optionsUtil = require("./util/options");
const mkdirp = require("./util/mkdirp");
const EOL = process.platform === "win32" ? "\r\n" : "\n";
// global.Binaryen = require("../lib/binaryen");
// Emscripten adds an `uncaughtException` listener to Binaryen that results in an additional
// useless code fragment on top of an actual error. suppress this:
if (process.removeAllListeners) process.removeAllListeners("uncaughtException");
@ -68,7 +70,7 @@ exports.sourceMapRoot = "assemblyscript:///";
exports.libraryPrefix = assemblyscript.LIBRARY_PREFIX;
/** Default Binaryen optimization level. */
exports.defaultOptimizeLevel = 2;
exports.defaultOptimizeLevel = 3;
/** Default Binaryen shrink level. */
exports.defaultShrinkLevel = 1;
@ -228,30 +230,18 @@ exports.main = function main(argv, options, callback) {
var parser = null;
// Include library files
if (!args.noLib) {
Object.keys(exports.libraryFiles).forEach(libPath => {
if (libPath.indexOf("/") >= 0) return; // in sub-directory: imported on demand
stats.parseCount++;
stats.parseTime += measure(() => {
parser = assemblyscript.parseFile(
exports.libraryFiles[libPath],
exports.libraryPrefix + libPath + ".ts",
false,
parser
);
});
});
} else { // always include builtins
Object.keys(exports.libraryFiles).forEach(libPath => {
if (libPath.indexOf("/") >= 0) return; // in sub-directory: imported on demand
stats.parseCount++;
stats.parseTime += measure(() => {
parser = assemblyscript.parseFile(
exports.libraryFiles["builtins"],
exports.libraryPrefix + "builtins.ts",
exports.libraryFiles[libPath],
exports.libraryPrefix + libPath + ".ts",
false,
parser
);
});
}
});
const customLibDirs = [];
if (args.lib) {
let lib = args.lib;
@ -287,6 +277,7 @@ exports.main = function main(argv, options, callback) {
function parseBacklog() {
var sourcePath, sourceText;
while ((sourcePath = parser.nextFile()) != null) {
sourceText = null;
// Load library file if explicitly requested
if (sourcePath.startsWith(exports.libraryPrefix)) {
@ -335,12 +326,12 @@ exports.main = function main(argv, options, callback) {
} else {
for (let i = 0, k = customLibDirs.length; i < k; ++i) {
const dir = customLibDirs[i];
sourceText = readFile(plainName + ".ts", customLibDirs[i]);
sourceText = readFile(plainName + ".ts", dir);
if (sourceText !== null) {
sourcePath = exports.libraryPrefix + plainName + ".ts";
break;
} else {
sourceText = readFile(indexName + ".ts", customLibDirs[i]);
sourceText = readFile(indexName + ".ts", dir);
if (sourceText !== null) {
sourcePath = exports.libraryPrefix + indexName + ".ts";
break;
@ -364,6 +355,26 @@ exports.main = function main(argv, options, callback) {
}
}
// Include runtime template before entry files so its setup runs first
{
let runtimeName = String(args.runtime);
let runtimePath = "rt/index-" + runtimeName;
let runtimeText = exports.libraryFiles[runtimePath];
if (runtimeText == null) {
runtimePath = runtimeName;
runtimeText = readFile(runtimePath + ".ts", baseDir);
if (runtimeText == null) {
return callback(Error("Runtime '" + runtimeName + "' not found."));
}
} else {
runtimePath = "~lib/" + runtimePath;
}
stats.parseCount++;
stats.parseTime += measure(() => {
parser = assemblyscript.parseFile(runtimeText, runtimePath, true, parser);
});
}
// Include entry files
for (let i = 0, k = argv.length; i < k; ++i) {
const filename = argv[i];
@ -387,11 +398,18 @@ exports.main = function main(argv, options, callback) {
stats.parseTime += measure(() => {
parser = assemblyscript.parseFile(sourceText, sourcePath, true, parser);
});
}
// Parse entry files
{
let code = parseBacklog();
if (code) return code;
}
// Call afterParse transform hook
applyTransform("afterParse", parser);
// Parse additional files, if any
{
let code = parseBacklog();
if (code) return code;
@ -423,17 +441,16 @@ exports.main = function main(argv, options, callback) {
assemblyscript.setImportMemory(compilerOptions, args.importMemory);
assemblyscript.setSharedMemory(compilerOptions, args.sharedMemory);
assemblyscript.setImportTable(compilerOptions, args.importTable);
assemblyscript.setExplicitStart(compilerOptions, args.explicitStart);
assemblyscript.setMemoryBase(compilerOptions, args.memoryBase >>> 0);
assemblyscript.setSourceMap(compilerOptions, args.sourceMap != null);
assemblyscript.setOptimizeLevelHints(compilerOptions, optimizeLevel, shrinkLevel);
if (!args.noLib) {
// Initialize default aliases
assemblyscript.setGlobalAlias(compilerOptions, "Math", "NativeMath");
assemblyscript.setGlobalAlias(compilerOptions, "Mathf", "NativeMathf");
assemblyscript.setGlobalAlias(compilerOptions, "abort", "~lib/env/abort");
assemblyscript.setGlobalAlias(compilerOptions, "trace", "~lib/env/trace");
}
// Initialize default aliases
assemblyscript.setGlobalAlias(compilerOptions, "Math", "NativeMath");
assemblyscript.setGlobalAlias(compilerOptions, "Mathf", "NativeMathf");
assemblyscript.setGlobalAlias(compilerOptions, "abort", "~lib/builtins/abort");
assemblyscript.setGlobalAlias(compilerOptions, "trace", "~lib/builtins/trace");
// Add or override aliases if specified
if (args.use) {
@ -463,15 +480,13 @@ exports.main = function main(argv, options, callback) {
var module;
stats.compileCount++;
(() => {
try {
stats.compileTime += measure(() => {
module = assemblyscript.compileProgram(program, compilerOptions);
});
} catch (e) {
return callback(e);
}
})();
try {
stats.compileTime += measure(() => {
module = assemblyscript.compileProgram(program, compilerOptions);
});
} catch (e) {
return callback(e);
}
if (checkDiagnostics(parser, stderr)) {
if (module) module.dispose();
return callback(Error("Compile error"));
@ -697,6 +712,9 @@ exports.main = function main(argv, options, callback) {
if (args.measure) {
printStats(stats, stderr);
}
if (args.printrtti) {
printRTTI(program, stderr);
}
return callback(null);
function readFileNode(filename, baseDir) {
@ -833,6 +851,15 @@ function printStats(stats, output) {
exports.printStats = printStats;
/** Prints runtime type information. */
function printRTTI(program, output) {
if (!output) output = process.stderr;
output.write("# Runtime type information (RTTI)\n");
output.write(assemblyscript.buildRTTI(program));
}
exports.printRTTI = printRTTI;
var allocBuffer = typeof global !== "undefined" && global.Buffer
? global.Buffer.allocUnsafe || function(len) { return new global.Buffer(len); }
: function(len) { return new Uint8Array(len) };