Fix an issue with asc not finding bundled library files in the browser; Minor cleanup

This commit is contained in:
dcodeIO 2018-03-21 23:27:53 +01:00
parent d4c46b036e
commit 00e6d613a9
12 changed files with 138 additions and 100 deletions

View File

@ -251,6 +251,7 @@ exports.main = function main(argv, options, callback) {
for (let i = 0, k = libDirs.length; i < k; ++i) { for (let i = 0, k = libDirs.length; i < k; ++i) {
if (exports.libraryFiles.hasOwnProperty(sourcePath)) { if (exports.libraryFiles.hasOwnProperty(sourcePath)) {
sourceText = exports.libraryFiles[sourcePath]; sourceText = exports.libraryFiles[sourcePath];
sourcePath += ".ts";
} else { } else {
sourceText = readFile(path.join( sourceText = readFile(path.join(
libDirs[i], libDirs[i],
@ -266,32 +267,33 @@ exports.main = function main(argv, options, callback) {
// Otherwise try nextFile.ts, nextFile/index.ts, (lib)/nextFile.ts // Otherwise try nextFile.ts, nextFile/index.ts, (lib)/nextFile.ts
} else { } else {
sourceText = readFile(path.join(baseDir, sourcePath + ".ts")); sourceText = readFile(path.join(baseDir, sourcePath + ".ts"));
if (sourceText === null) { if (sourceText !== null) {
sourcePath += ".ts";
} else {
sourceText = readFile(path.join(baseDir, sourcePath, "index.ts")); sourceText = readFile(path.join(baseDir, sourcePath, "index.ts"));
if (sourceText === null) { if (sourceText !== null) {
for (let i = 0, k = libDirs.length; i < k; ++i) { sourcePath += "/index.ts";
const dir = libDirs[i]; } else {
const key = exports.libraryPrefix + sourcePath; const key = exports.libraryPrefix + sourcePath;
if (exports.libraryFiles.hasOwnProperty(key)) { if (exports.libraryFiles.hasOwnProperty(key)) {
sourceText = exports.libraryFiles[key]; sourceText = exports.libraryFiles[key];
sourcePath = key + ".ts";
} else { } else {
for (let i = 0, k = libDirs.length; i < k; ++i) {
const dir = libDirs[i];
sourceText = readFile(path.join(dir, sourcePath + ".ts")); sourceText = readFile(path.join(dir, sourcePath + ".ts"));
if (sourceText !== null) { if (sourceText !== null) {
sourcePath = exports.libraryPrefix + sourcePath + ".ts"; sourcePath = exports.libraryPrefix + sourcePath + ".ts";
break; break;
} }
} }
}
if (sourceText === null) { if (sourceText === null) {
return callback( return callback(
Error("Import file '" + sourcePath + ".ts' not found.") Error("Import file '" + sourcePath + ".ts' not found.")
); );
} }
} else {
sourcePath += "/index.ts";
} }
} else { }
sourcePath += ".ts";
} }
} }
stats.parseCount++; stats.parseCount++;

2
dist/asc.js vendored

File diff suppressed because one or more lines are too long

2
dist/asc.js.map vendored

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View File

@ -109,7 +109,7 @@ export abstract class Node {
/** Common flags indicating specific traits. */ /** Common flags indicating specific traits. */
flags: CommonFlags = CommonFlags.NONE; flags: CommonFlags = CommonFlags.NONE;
/** Tests if this node has a specific flag or flags. */ /** Tests if this node has the specified flag or flags. */
is(flag: CommonFlags): bool { return (this.flags & flag) == flag; } is(flag: CommonFlags): bool { return (this.flags & flag) == flag; }
/** Tests if this node has one of the specified flags. */ /** Tests if this node has one of the specified flags. */
isAny(flag: CommonFlags): bool { return (this.flags & flag) != 0; } isAny(flag: CommonFlags): bool { return (this.flags & flag) != 0; }

View File

@ -192,7 +192,7 @@ export function compileCall(
compiler.compileExpressionRetainType(operands[0], Type.i32, false); compiler.compileExpressionRetainType(operands[0], Type.i32, false);
type = compiler.currentType; type = compiler.currentType;
compiler.currentType = Type.bool; compiler.currentType = Type.bool;
let classType = type.classType; let classType = type.classReference;
if (classType) { if (classType) {
let stringPrototype = compiler.program.elementsLookup.get("String"); let stringPrototype = compiler.program.elementsLookup.get("String");
if (stringPrototype) { if (stringPrototype) {
@ -224,7 +224,7 @@ export function compileCall(
compiler.compileExpressionRetainType(operands[0], Type.i32, false); compiler.compileExpressionRetainType(operands[0], Type.i32, false);
type = compiler.currentType; type = compiler.currentType;
compiler.currentType = Type.bool; compiler.currentType = Type.bool;
let classType = type.classType; let classType = type.classReference;
return classType != null && classType.prototype.fnIndexedGet != null return classType != null && classType.prototype.fnIndexedGet != null
? module.createI32(1) ? module.createI32(1)
: module.createI32(0); : module.createI32(0);
@ -407,7 +407,7 @@ export function compileCall(
break; break;
} }
case TypeKind.USIZE: { case TypeKind.USIZE: {
if (compiler.currentType.isReference) { if (compiler.currentType.is(TypeFlags.REFERENCE)) {
compiler.error( compiler.error(
DiagnosticCode.Operation_not_supported, DiagnosticCode.Operation_not_supported,
reportNode.range reportNode.range
@ -480,7 +480,7 @@ export function compileCall(
break; break;
} }
case TypeKind.USIZE: { case TypeKind.USIZE: {
if (compiler.currentType.isReference) { if (compiler.currentType.is(TypeFlags.REFERENCE)) {
compiler.error( compiler.error(
DiagnosticCode.Operation_not_supported, DiagnosticCode.Operation_not_supported,
reportNode.range reportNode.range
@ -553,7 +553,7 @@ export function compileCall(
break; break;
} }
case TypeKind.USIZE: { case TypeKind.USIZE: {
if (compiler.currentType.isReference) { if (compiler.currentType.is(TypeFlags.REFERENCE)) {
compiler.error( compiler.error(
DiagnosticCode.Operation_not_supported, DiagnosticCode.Operation_not_supported,
reportNode.range reportNode.range
@ -640,7 +640,7 @@ export function compileCall(
break; break;
} }
case TypeKind.USIZE: { case TypeKind.USIZE: {
if (compiler.currentType.isReference) { if (compiler.currentType.is(TypeFlags.REFERENCE)) {
compiler.error( compiler.error(
DiagnosticCode.Operation_not_supported, DiagnosticCode.Operation_not_supported,
reportNode.range reportNode.range
@ -726,7 +726,7 @@ export function compileCall(
break; break;
} }
case TypeKind.USIZE: { case TypeKind.USIZE: {
if (compiler.currentType.isReference) { if (compiler.currentType.is(TypeFlags.REFERENCE)) {
compiler.error( compiler.error(
DiagnosticCode.Operation_not_supported, DiagnosticCode.Operation_not_supported,
reportNode.range reportNode.range
@ -849,7 +849,7 @@ export function compileCall(
break; break;
} }
case TypeKind.USIZE: { case TypeKind.USIZE: {
if (compiler.currentType.isReference) { if (compiler.currentType.is(TypeFlags.REFERENCE)) {
compiler.error( compiler.error(
DiagnosticCode.Operation_not_supported, DiagnosticCode.Operation_not_supported,
reportNode.range reportNode.range
@ -1001,7 +1001,7 @@ export function compileCall(
break; break;
} }
case TypeKind.USIZE: { case TypeKind.USIZE: {
if (compiler.currentType.isReference) { if (compiler.currentType.is(TypeFlags.REFERENCE)) {
compiler.error( compiler.error(
DiagnosticCode.Operation_not_supported, DiagnosticCode.Operation_not_supported,
reportNode.range reportNode.range
@ -1155,7 +1155,7 @@ export function compileCall(
break; break;
} }
case TypeKind.USIZE: { case TypeKind.USIZE: {
if (compiler.currentType.isReference) { if (compiler.currentType.is(TypeFlags.REFERENCE)) {
compiler.error( compiler.error(
DiagnosticCode.Operation_not_supported, DiagnosticCode.Operation_not_supported,
reportNode.range reportNode.range
@ -1230,7 +1230,7 @@ export function compileCall(
} }
switch (compiler.currentType.kind) { switch (compiler.currentType.kind) {
case TypeKind.USIZE: { case TypeKind.USIZE: {
if (compiler.currentType.isReference) { if (compiler.currentType.is(TypeFlags.REFERENCE)) {
compiler.error( compiler.error(
DiagnosticCode.Operation_not_supported, DiagnosticCode.Operation_not_supported,
reportNode.range reportNode.range
@ -1295,7 +1295,7 @@ export function compileCall(
} }
switch (compiler.currentType.kind) { switch (compiler.currentType.kind) {
case TypeKind.USIZE: { case TypeKind.USIZE: {
if (compiler.currentType.isReference) { if (compiler.currentType.is(TypeFlags.REFERENCE)) {
compiler.error( compiler.error(
DiagnosticCode.Operation_not_supported, DiagnosticCode.Operation_not_supported,
reportNode.range reportNode.range
@ -1411,7 +1411,7 @@ export function compileCall(
} }
switch (compiler.currentType.kind) { switch (compiler.currentType.kind) {
case TypeKind.USIZE: { case TypeKind.USIZE: {
if (compiler.currentType.isReference) { if (compiler.currentType.is(TypeFlags.REFERENCE)) {
compiler.error( compiler.error(
DiagnosticCode.Operation_not_supported, DiagnosticCode.Operation_not_supported,
reportNode.range reportNode.range
@ -1481,7 +1481,7 @@ export function compileCall(
break; break;
} }
case TypeKind.USIZE: { case TypeKind.USIZE: {
if (typeArguments[0].isReference) { if (typeArguments[0].is(TypeFlags.REFERENCE)) {
compiler.error( compiler.error(
DiagnosticCode.Operation_not_supported, DiagnosticCode.Operation_not_supported,
reportNode.range reportNode.range
@ -1612,7 +1612,7 @@ export function compileCall(
} }
switch (compiler.currentType.kind) { switch (compiler.currentType.kind) {
case TypeKind.USIZE: { case TypeKind.USIZE: {
if (compiler.currentType.isReference) { if (compiler.currentType.is(TypeFlags.REFERENCE)) {
compiler.error( compiler.error(
DiagnosticCode.Operation_not_supported, DiagnosticCode.Operation_not_supported,
reportNode.range reportNode.range

View File

@ -2064,6 +2064,7 @@ export class Compiler extends DiagnosticEmitter {
// void to any // void to any
if (fromType.kind == TypeKind.VOID) { if (fromType.kind == TypeKind.VOID) {
assert(toType.kind != TypeKind.VOID); // convertExpression should not be called with void -> void
this.error( this.error(
DiagnosticCode.Type_0_is_not_assignable_to_type_1, DiagnosticCode.Type_0_is_not_assignable_to_type_1,
reportNode.range, fromType.toString(), toType.toString() reportNode.range, fromType.toString(), toType.toString()
@ -4021,7 +4022,7 @@ export class Compiler extends DiagnosticEmitter {
// indirect call: index argument with signature // indirect call: index argument with signature
case ElementKind.LOCAL: { case ElementKind.LOCAL: {
if (signature = (<Local>element).type.functionType) { if (signature = (<Local>element).type.signatureReference) {
indexArg = module.createGetLocal((<Local>element).index, NativeType.I32); indexArg = module.createGetLocal((<Local>element).index, NativeType.I32);
break; break;
} else { } else {
@ -4033,7 +4034,7 @@ export class Compiler extends DiagnosticEmitter {
} }
} }
case ElementKind.GLOBAL: { case ElementKind.GLOBAL: {
if (signature = (<Global>element).type.functionType) { if (signature = (<Global>element).type.signatureReference) {
indexArg = module.createGetGlobal((<Global>element).internalName, (<Global>element).type.toNativeType()); indexArg = module.createGetGlobal((<Global>element).internalName, (<Global>element).type.toNativeType());
break; break;
} else { } else {
@ -4046,7 +4047,7 @@ export class Compiler extends DiagnosticEmitter {
} }
case ElementKind.FIELD: { case ElementKind.FIELD: {
let type = (<Field>element).type; let type = (<Field>element).type;
if (signature = type.functionType) { if (signature = type.signatureReference) {
let targetExpr = this.compileExpression(assert(resolved.targetExpression), type); let targetExpr = this.compileExpression(assert(resolved.targetExpression), type);
indexArg = module.createLoad( indexArg = module.createLoad(
4, 4,
@ -4425,7 +4426,7 @@ export class Compiler extends DiagnosticEmitter {
declaration declaration
); );
if (!instance) return this.module.createUnreachable(); if (!instance) return this.module.createUnreachable();
this.currentType = Type.u32.asFunction(instance.signature); // TODO: get cached type? this.currentType = instance.signature.type; // TODO: get cached type?
// NOTE that, in order to make this work in every case, the function must be represented by a // NOTE that, in order to make this work in every case, the function must be represented by a
// value, so we add it and rely on the optimizer to figure out where it can be called directly. // value, so we add it and rely on the optimizer to figure out where it can be called directly.
var index = this.ensureFunctionTableEntry(instance); // reports var index = this.ensureFunctionTableEntry(instance); // reports
@ -4449,7 +4450,7 @@ export class Compiler extends DiagnosticEmitter {
switch (expression.kind) { switch (expression.kind) {
case NodeKind.NULL: { case NodeKind.NULL: {
let options = this.options; let options = this.options;
if (!contextualType.classType) { if (!contextualType.classReference) {
this.currentType = options.usizeType; this.currentType = options.usizeType;
} }
return options.isWasm64 return options.isWasm64
@ -4558,7 +4559,7 @@ export class Compiler extends DiagnosticEmitter {
); );
if (!(instance && this.compileFunction(instance))) return module.createUnreachable(); if (!(instance && this.compileFunction(instance))) return module.createUnreachable();
let index = this.ensureFunctionTableEntry(instance); let index = this.ensureFunctionTableEntry(instance);
this.currentType = Type.u32.asFunction(instance.signature); this.currentType = instance.signature.type;
return this.module.createI32(index); return this.module.createI32(index);
} }
} }
@ -4579,7 +4580,7 @@ export class Compiler extends DiagnosticEmitter {
switch (expression.literalKind) { switch (expression.literalKind) {
case LiteralKind.ARRAY: { case LiteralKind.ARRAY: {
assert(!implicitNegate); assert(!implicitNegate);
let classType = contextualType.classType; let classType = contextualType.classReference;
if ( if (
classType && classType &&
classType.prototype == this.program.elementsLookup.get("Array") classType.prototype == this.program.elementsLookup.get("Array")
@ -5139,7 +5140,7 @@ export class Compiler extends DiagnosticEmitter {
switch (expression.operator) { switch (expression.operator) {
case Token.PLUS_PLUS: { case Token.PLUS_PLUS: {
if (currentType.isReference) { if (currentType.is(TypeFlags.REFERENCE)) {
this.error( this.error(
DiagnosticCode.Operation_not_supported, DiagnosticCode.Operation_not_supported,
expression.range expression.range
@ -5199,7 +5200,7 @@ export class Compiler extends DiagnosticEmitter {
break; break;
} }
case Token.MINUS_MINUS: { case Token.MINUS_MINUS: {
if (currentType.isReference) { if (currentType.is(TypeFlags.REFERENCE)) {
this.error( this.error(
DiagnosticCode.Operation_not_supported, DiagnosticCode.Operation_not_supported,
expression.range expression.range
@ -5323,7 +5324,7 @@ export class Compiler extends DiagnosticEmitter {
switch (expression.operator) { switch (expression.operator) {
case Token.PLUS: { case Token.PLUS: {
if (currentType.isReference) { if (currentType.is(TypeFlags.REFERENCE)) {
this.error( this.error(
DiagnosticCode.Operation_not_supported, DiagnosticCode.Operation_not_supported,
expression.range expression.range
@ -5343,7 +5344,7 @@ export class Compiler extends DiagnosticEmitter {
break; break;
} }
case Token.MINUS: { case Token.MINUS: {
if (currentType.isReference) { if (currentType.is(TypeFlags.REFERENCE)) {
this.error( this.error(
DiagnosticCode.Operation_not_supported, DiagnosticCode.Operation_not_supported,
expression.range expression.range
@ -5382,7 +5383,7 @@ export class Compiler extends DiagnosticEmitter {
break; break;
} }
case TypeKind.USIZE: { case TypeKind.USIZE: {
if (currentType.isReference) { if (currentType.is(TypeFlags.REFERENCE)) {
this.error( this.error(
DiagnosticCode.Operation_not_supported, DiagnosticCode.Operation_not_supported,
expression.range expression.range
@ -5419,7 +5420,7 @@ export class Compiler extends DiagnosticEmitter {
break; break;
} }
case Token.PLUS_PLUS: { case Token.PLUS_PLUS: {
if (currentType.isReference) { if (currentType.is(TypeFlags.REFERENCE)) {
this.error( this.error(
DiagnosticCode.Operation_not_supported, DiagnosticCode.Operation_not_supported,
expression.range expression.range
@ -5447,7 +5448,7 @@ export class Compiler extends DiagnosticEmitter {
break; break;
} }
case TypeKind.USIZE: { case TypeKind.USIZE: {
if (currentType.isReference) { if (currentType.is(TypeFlags.REFERENCE)) {
this.error( this.error(
DiagnosticCode.Operation_not_supported, DiagnosticCode.Operation_not_supported,
expression.range expression.range
@ -5483,7 +5484,7 @@ export class Compiler extends DiagnosticEmitter {
break; break;
} }
case Token.MINUS_MINUS: { case Token.MINUS_MINUS: {
if (currentType.isReference) { if (currentType.is(TypeFlags.REFERENCE)) {
this.error( this.error(
DiagnosticCode.Operation_not_supported, DiagnosticCode.Operation_not_supported,
expression.range expression.range
@ -5511,7 +5512,7 @@ export class Compiler extends DiagnosticEmitter {
break; break;
} }
case TypeKind.USIZE: { case TypeKind.USIZE: {
if (currentType.isReference) { if (currentType.is(TypeFlags.REFERENCE)) {
this.error( this.error(
DiagnosticCode.Operation_not_supported, DiagnosticCode.Operation_not_supported,
expression.range expression.range
@ -5560,7 +5561,7 @@ export class Compiler extends DiagnosticEmitter {
break; break;
} }
case Token.TILDE: { case Token.TILDE: {
if (currentType.isReference) { if (currentType.is(TypeFlags.REFERENCE)) {
this.error( this.error(
DiagnosticCode.Operation_not_supported, DiagnosticCode.Operation_not_supported,
expression.range expression.range
@ -5591,7 +5592,7 @@ export class Compiler extends DiagnosticEmitter {
break; break;
} }
case TypeKind.USIZE: { case TypeKind.USIZE: {
if (currentType.isReference) { if (currentType.is(TypeFlags.REFERENCE)) {
this.error( this.error(
DiagnosticCode.Operation_not_supported, DiagnosticCode.Operation_not_supported,
expression.range expression.range

View File

@ -152,15 +152,15 @@ function i64_to_f64(value: I64): f64 {
import { CharCode } from "../../util"; import { CharCode } from "../../util";
@global @global
function i64_to_string(value: I64): string { function i64_to_string(value: I64, unsigned: bool = false): string {
var chars = new Array<u16>(); var chars = new Array<u16>();
if (value < 0) { if (!unsigned && value < 0) {
chars.push(CharCode.MINUS); chars.push(CharCode.MINUS);
value = -value; value = -value;
} }
do { do {
chars.push(CharCode._0 + (value % 10)); chars.push(CharCode._0 + (<u64>value % 10));
value /= 10; value = <u64>value / 10;
} while (value); } while (value);
return String.fromCharCodes(chars); return String.fromCharCodes(chars);
} }

View File

@ -1715,27 +1715,27 @@ export class Program extends DiagnosticEmitter {
case ElementKind.GLOBAL: case ElementKind.GLOBAL:
case ElementKind.LOCAL: case ElementKind.LOCAL:
case ElementKind.FIELD: { case ElementKind.FIELD: {
if (!(targetType = (<VariableLikeElement>target).type).classType) { if (!(targetType = (<VariableLikeElement>target).type).classReference) {
this.error( this.error(
DiagnosticCode.Property_0_does_not_exist_on_type_1, DiagnosticCode.Property_0_does_not_exist_on_type_1,
propertyAccess.property.range, propertyName, targetType.toString() propertyAccess.property.range, propertyName, targetType.toString()
); );
return null; return null;
} }
target = <Class>targetType.classType; target = <Class>targetType.classReference;
break; break;
} }
case ElementKind.PROPERTY: { case ElementKind.PROPERTY: {
let getter = assert((<Property>target).getterPrototype).resolve(); // reports let getter = assert((<Property>target).getterPrototype).resolve(); // reports
if (!getter) return null; if (!getter) return null;
if (!(targetType = getter.signature.returnType).classType) { if (!(targetType = getter.signature.returnType).classReference) {
this.error( this.error(
DiagnosticCode.Property_0_does_not_exist_on_type_1, DiagnosticCode.Property_0_does_not_exist_on_type_1,
propertyAccess.property.range, propertyName, targetType.toString() propertyAccess.property.range, propertyName, targetType.toString()
); );
return null; return null;
} }
target = <Class>targetType.classType; target = <Class>targetType.classReference;
break; break;
} }
} }
@ -1799,8 +1799,8 @@ export class Program extends DiagnosticEmitter {
case ElementKind.LOCAL: case ElementKind.LOCAL:
case ElementKind.FIELD: { case ElementKind.FIELD: {
let type = (<VariableLikeElement>target).type; let type = (<VariableLikeElement>target).type;
if (type.classType) { if (type.classReference) {
let indexedGetName = (target = type.classType).prototype.fnIndexedGet; let indexedGetName = (target = type.classReference).prototype.fnIndexedGet;
let indexedGet: Element | null; let indexedGet: Element | null;
if ( if (
indexedGetName != null && indexedGetName != null &&
@ -1808,7 +1808,7 @@ export class Program extends DiagnosticEmitter {
(indexedGet = target.members.get(indexedGetName)) && (indexedGet = target.members.get(indexedGetName)) &&
indexedGet.kind == ElementKind.FUNCTION_PROTOTYPE indexedGet.kind == ElementKind.FUNCTION_PROTOTYPE
) { ) {
return resolvedElement.set(indexedGet).withTarget(type.classType, targetExpression); return resolvedElement.set(indexedGet).withTarget(type.classReference, targetExpression);
} }
} }
break; break;
@ -1832,7 +1832,7 @@ export class Program extends DiagnosticEmitter {
case NodeKind.ASSERTION: { case NodeKind.ASSERTION: {
let type = this.resolveType((<AssertionExpression>expression).toType); // reports let type = this.resolveType((<AssertionExpression>expression).toType); // reports
if (type) { if (type) {
let classType = type.classType; let classType = type.classReference;
if (classType) { if (classType) {
if (!resolvedElement) resolvedElement = new ResolvedElement(); if (!resolvedElement) resolvedElement = new ResolvedElement();
return resolvedElement.set(classType); return resolvedElement.set(classType);
@ -1897,12 +1897,12 @@ export class Program extends DiagnosticEmitter {
); );
if (instance) { if (instance) {
let returnType = instance.signature.returnType; let returnType = instance.signature.returnType;
let classType = returnType.classType; let classType = returnType.classReference;
if (classType) { if (classType) {
if (!resolvedElement) resolvedElement = new ResolvedElement(); if (!resolvedElement) resolvedElement = new ResolvedElement();
return resolvedElement.set(classType); return resolvedElement.set(classType);
} else { } else {
let signature = returnType.functionType; let signature = returnType.signatureReference;
if (signature) { if (signature) {
let functionTarget = signature.cachedFunctionTarget; let functionTarget = signature.cachedFunctionTarget;
if (!functionTarget) { if (!functionTarget) {
@ -2864,7 +2864,7 @@ export class ClassPrototype extends Element {
if (declaration.extendsType) { if (declaration.extendsType) {
let baseClassType = this.program.resolveType(declaration.extendsType, null); // reports let baseClassType = this.program.resolveType(declaration.extendsType, null); // reports
if (!baseClassType) return null; if (!baseClassType) return null;
if (!(baseClass = baseClassType.classType)) { if (!(baseClass = baseClassType.classReference)) {
this.program.error( this.program.error(
DiagnosticCode.A_class_may_only_extend_another_class, DiagnosticCode.A_class_may_only_extend_another_class,
declaration.extendsType.range declaration.extendsType.range
@ -3198,7 +3198,6 @@ export class Flow {
/** Tests if this flow has the specified flag or flags. */ /** Tests if this flow has the specified flag or flags. */
is(flag: FlowFlags): bool { return (this.flags & flag) == flag; } is(flag: FlowFlags): bool { return (this.flags & flag) == flag; }
/** Sets the specified flag or flags. */ /** Sets the specified flag or flags. */
set(flag: FlowFlags): void { this.flags |= flag; } set(flag: FlowFlags): void { this.flags |= flag; }

View File

@ -94,10 +94,10 @@ export class Type {
size: u32; size: u32;
/** Size in bytes. Ceiled to 8-bits. */ /** Size in bytes. Ceiled to 8-bits. */
byteSize: i32; byteSize: i32;
/** Underlying class type, if a class type. */ /** Underlying class reference, if a class type. */
classType: Class | null; classReference: Class | null;
/** Underlying function type, if a function type. */ /** Underlying function reference, if a function type. */
functionType: Signature | null; signatureReference: Signature | null;
/** Respective nullable type, if non-nullable. */ /** Respective nullable type, if non-nullable. */
nullableType: Type | null = null; nullableType: Type | null = null;
/** Respective non-nullable type, if nullable. */ /** Respective non-nullable type, if nullable. */
@ -109,7 +109,8 @@ export class Type {
this.flags = flags; this.flags = flags;
this.size = size; this.size = size;
this.byteSize = <i32>ceil<f64>(<f64>size / 8); this.byteSize = <i32>ceil<f64>(<f64>size / 8);
this.classType = null; this.classReference = null;
this.signatureReference = null;
this.nonNullableType = this; this.nonNullableType = this;
} }
@ -128,37 +129,30 @@ export class Type {
/** Tests if this type has any of the specified flags. */ /** Tests if this type has any of the specified flags. */
isAny(flags: TypeFlags): bool { return (this.flags & flags) != 0; } isAny(flags: TypeFlags): bool { return (this.flags & flags) != 0; }
/** Tests if this type is a class type. */
get isClass(): bool { return this.classType != null; }
/** Tests if this type is a function type. */
get isFunction(): bool { return this.functionType != null; }
/** Tests if this type is a reference type. */
get isReference(): bool { return this.classType != null || this.functionType != null; }
/** Composes a class type from this type and a class. */ /** Composes a class type from this type and a class. */
asClass(classType: Class): Type { asClass(classType: Class): Type {
assert(this.kind == TypeKind.USIZE && !this.classType); assert(this.kind == TypeKind.USIZE && !this.classReference);
var ret = new Type(this.kind, this.flags & ~TypeFlags.VALUE | TypeFlags.REFERENCE, this.size); var ret = new Type(this.kind, this.flags & ~TypeFlags.VALUE | TypeFlags.REFERENCE, this.size);
ret.classType = classType; ret.classReference = classType;
return ret; return ret;
} }
/** Composes a function type from this type and a function. */ /** Composes a function type from this type and a function. */
asFunction(functionType: Signature): Type { asFunction(signature: Signature): Type {
assert(this.kind == TypeKind.U32 && !this.functionType); assert(this.kind == TypeKind.U32 && !this.signatureReference);
var ret = new Type(this.kind, this.flags & ~TypeFlags.VALUE | TypeFlags.REFERENCE, this.size); var ret = new Type(this.kind, this.flags & ~TypeFlags.VALUE | TypeFlags.REFERENCE, this.size);
ret.functionType = functionType; ret.signatureReference = signature;
return ret; return ret;
} }
/** Composes the respective nullable type of this type. */ /** Composes the respective nullable type of this type. */
asNullable(): Type { asNullable(): Type {
assert(this.isReference); assert(this.is(TypeFlags.REFERENCE));
if (!this.nullableType) { if (!this.nullableType) {
assert(!this.is(TypeFlags.NULLABLE)); assert(!this.is(TypeFlags.NULLABLE));
this.nullableType = new Type(this.kind, this.flags | TypeFlags.NULLABLE, this.size); this.nullableType = new Type(this.kind, this.flags | TypeFlags.NULLABLE, this.size);
this.nullableType.classType = this.classType; // either a class reference this.nullableType.classReference = this.classReference; // either a class reference
this.nullableType.functionType = this.functionType; // or a function reference this.nullableType.signatureReference = this.signatureReference; // or a function reference
} }
return this.nullableType; return this.nullableType;
} }
@ -169,19 +163,19 @@ export class Type {
var targetClass: Class | null; var targetClass: Class | null;
var currentFunction: Signature | null; var currentFunction: Signature | null;
var targetFunction: Signature | null; var targetFunction: Signature | null;
if (this.isReference) { if (this.is(TypeFlags.REFERENCE)) {
if (target.isReference) { if (target.is(TypeFlags.REFERENCE)) {
if (currentClass = this.classType) { if (currentClass = this.classReference) {
if (targetClass = target.classType) { if (targetClass = target.classReference) {
return currentClass.isAssignableTo(targetClass); return currentClass.isAssignableTo(targetClass);
} }
} else if (currentFunction = this.functionType) { } else if (currentFunction = this.signatureReference) {
if (targetFunction = target.functionType) { if (targetFunction = target.signatureReference) {
return currentFunction.isAssignableTo(targetFunction); return currentFunction.isAssignableTo(targetFunction);
} }
} }
} }
} else if (!target.isReference) { } else if (!target.is(TypeFlags.REFERENCE)) {
if (this.is(TypeFlags.INTEGER)) { if (this.is(TypeFlags.INTEGER)) {
if (target.is(TypeFlags.INTEGER)) { if (target.is(TypeFlags.INTEGER)) {
if (!signednessIsImportant || this.is(TypeFlags.SIGNED) == target.is(TypeFlags.SIGNED)) { if (!signednessIsImportant || this.is(TypeFlags.SIGNED) == target.is(TypeFlags.SIGNED)) {
@ -222,14 +216,14 @@ export class Type {
case TypeKind.U8: return "u8"; case TypeKind.U8: return "u8";
case TypeKind.U16: return "u16"; case TypeKind.U16: return "u16";
case TypeKind.U32: { case TypeKind.U32: {
let functionType = this.functionType; let functionType = this.signatureReference;
return kindOnly || !functionType return kindOnly || !functionType
? "u32" ? "u32"
: functionType.toString(true); : functionType.toString(true);
} }
case TypeKind.U64: return "u64"; case TypeKind.U64: return "u64";
case TypeKind.USIZE: { case TypeKind.USIZE: {
let classType = this.classType; let classType = this.classReference;
return kindOnly || !classType return kindOnly || !classType
? "usize" ? "usize"
: classType.toString(); : classType.toString();
@ -480,6 +474,8 @@ export class Signature {
hasRest: bool; hasRest: bool;
/** Cached {@link FunctionTarget}. */ /** Cached {@link FunctionTarget}. */
cachedFunctionTarget: FunctionTarget | null = null; cachedFunctionTarget: FunctionTarget | null = null;
/** Respective function type. */
type: Type;
/** Constructs a new signature. */ /** Constructs a new signature. */
constructor( constructor(
@ -493,6 +489,7 @@ export class Signature {
this.returnType = returnType ? returnType : Type.void; this.returnType = returnType ? returnType : Type.void;
this.thisType = thisType; this.thisType = thisType;
this.hasRest = false; this.hasRest = false;
this.type = Type.u32.asFunction(this);
} }
/** Gets the known or, alternatively, generic parameter name at the specified index. */ /** Gets the known or, alternatively, generic parameter name at the specified index. */

39
tests/browser-asc.js Normal file
View File

@ -0,0 +1,39 @@
const asc = require("../dist/asc.js");
const stdout = asc.createMemoryStream();
const stderr = asc.createMemoryStream();
const files = {
"/module.ts": `import "allocator/arena";`
};
asc.main([
"./module.ts",
"--textFile"
], {
stdout: stdout,
stderr: stderr,
readFile: (name) => {
console.log("readFile: " + name);
if (files.hasOwnProperty(name)) {
return files[name];
}
return null;
},
writeFile: (name, data) => {
console.log("writeFile: " + name);
},
listFiles: (dirname) => {
console.log("listFiles: " + dirname);
return [];
}
}, err => {
if (err) {
console.log(">>> THROWN >>>");
console.log(err);
}
console.log(">>> STDOUT >>>");
process.stdout.write(stdout.toString());
console.log(">>> STDERR >>>");
process.stdout.write(stderr.toString());
});